Browse Source

Merge pull request #13360 from rraallvv/cache_pruning_2.1

Fixes for SCons shared cache for Travis-CI and AppVeyor-CI (2.1)
Rémi Verschelde 7 years ago
parent
commit
b0b1e2e99e

+ 5 - 4
.appveyor.yml

@@ -3,8 +3,8 @@ os: Visual Studio 2015
 environment:
   HOME: "%HOMEDRIVE%%HOMEPATH%"
   PYTHON: C:\Python27
-  SCONS_CACHE: "%HOME%\\scons_cache"
-  SCONS_CACHE_LIMIT: 128
+  SCONS_CACHE_ROOT: "%HOME%\\scons_cache"
+  SCONS_CACHE_LIMIT: 512
   matrix:
     - VS: C:\Program Files (x86)\Microsoft Visual Studio 14.0\VC\vcvarsall.bat
       GD_PLATFORM: windows
@@ -13,7 +13,7 @@ environment:
       ARCH: amd64
 
 cache:
-  - "%SCONS_CACHE%"
+  - "%SCONS_CACHE_ROOT%"
 
 install:
   - SET "PATH=%PYTHON%;%PYTHON%\\Scripts;%PATH%"
@@ -25,6 +25,7 @@ before_build:
   - python --version
   - scons --version
   - cl.exe
+  - SET "SCONS_CACHE=%SCONS_CACHE_ROOT%\2.1"
 
 build_script:
-- scons platform=%GD_PLATFORM% target=%TARGET% tools=%TOOLS% progress=no
+- scons platform=%GD_PLATFORM% target=%TARGET% tools=%TOOLS% verbose=yes progress=no

+ 8 - 8
.travis.yml

@@ -5,7 +5,7 @@ sudo: false
 env:
   global:
     - SCONS_CACHE=$HOME/.scons_cache
-    - SCONS_CACHE_LIMIT=128
+    - SCONS_CACHE_LIMIT=1024
 
 cache:
   directories:
@@ -16,22 +16,22 @@ matrix:
     - env: STATIC_CHECKS=yes
       os: linux
       compiler: clang
-    - env: GODOT_TARGET=x11 TOOLS=yes
+    - env: GODOT_TARGET=x11 TOOLS=yes CACHE_NAME=${GODOT_TARGET}-gcc-tools
       os: linux
       compiler: gcc
-    #- env: GODOT_TARGET=x11 TOOLS=no
+    #- env: GODOT_TARGET=x11 TOOLS=no CACHE_NAME=${GODOT_TARGET}-clang
     #  os: linux
     #  compiler: clang
-    #- env: GODOT_TARGET=windows TOOLS=yes
+    #- env: GODOT_TARGET=windows TOOLS=yes CACHE_NAME=${GODOT_TARGET}-gcc-tools
     #  os: linux
     #  compiler: gcc
-    - env: GODOT_TARGET=android TOOLS=no
+    - env: GODOT_TARGET=android TOOLS=no CACHE_NAME=${GODOT_TARGET}-gcc
       os: linux
       compiler: gcc
-    - env: GODOT_TARGET=osx TOOLS=yes
+    - env: GODOT_TARGET=osx TOOLS=yes CACHE_NAME=${GODOT_TARGET}-clang-tools
       os: osx
       compiler: clang
-    #- env: GODOT_TARGET=iphone TOOLS=no
+    #- env: GODOT_TARGET=iphone TOOLS=no CACHE_NAME=${GODOT_TARGET}-clang
     #  os: osx
     #  compiler: clang
 
@@ -78,5 +78,5 @@ script:
   - if [ "$STATIC_CHECKS" = "yes" ]; then
       sh ./misc/travis/clang-format.sh;
     else
-      scons -j 2 platform=$GODOT_TARGET progress=no verbose=yes CXX=$CXX builtin_openssl=yes;
+      scons -j 2 platform=$GODOT_TARGET CXX=$CXX builtin_openssl=yes verbose=yes progress=no;
     fi

+ 53 - 30
SConstruct

@@ -435,6 +435,7 @@ node_count_interval = 1
 node_pruning = 8 # Number of nodes to process before prunning the cache
 if ('env' in locals()):
     node_count_fname = str(env.Dir('#')) + '/.scons_node_count'
+show_progress = env['progress'] == 'yes'
 
 import time, math
 
@@ -445,23 +446,26 @@ class cache_progress:
         self.path = path
         self.limit = limit
         self.exponent_scale = math.log(2) / half_life
+        if env['verbose'] == 'yes' and path != None:
+            screen.write('Current cache limit is ' + self.convert_size(limit) + ' (used: ' + self.convert_size(self.get_size(path)) + ')\n')
         self.pruning = node_pruning
         self.delete(self.file_list())
 
     def __call__(self, node, *args, **kw):
-        global node_count, node_count_max, node_count_interval, node_count_fname, node_pruning
-        # Print the progress percentage
-        node_count += node_count_interval
-        if (node_count_max > 0 and node_count <= node_count_max):
-            screen.write('\r[%3d%%] ' % (node_count * 100 / node_count_max))
-            screen.flush()
-        elif (node_count_max > 0 and node_count > node_count_max):
-            screen.write('\r[100%] ')
-            screen.flush()
-        else:
-            screen.write('\r[Initial build] ')
-            screen.flush()
-        # Prune if the number of nodes proccessed is 'node_pruning' or bigger
+        global node_count, node_count_max, node_count_interval, node_count_fname, node_pruning, show_progress
+        if show_progress:
+            # Print the progress percentage
+            node_count += node_count_interval
+            if (node_count_max > 0 and node_count <= node_count_max):
+                screen.write('\r[%3d%%] ' % (node_count * 100 / node_count_max))
+                screen.flush()
+            elif (node_count_max > 0 and node_count > node_count_max):
+                screen.write('\r[100%] ')
+                screen.flush()
+            else:
+                screen.write('\r[Initial build] ')
+                screen.flush()
+        # Prune if the number of nodes processed is 'node_pruning' or bigger
         self.pruning -= node_count_interval
         if self.pruning <= 0:
             self.pruning = node_pruning
@@ -470,8 +474,9 @@ class cache_progress:
     def delete(self, files):
         if len(files) == 0:
             return
-        # Utter something
-        sys.stderr.write('\rPurging %d %s from cache...\n' % (len(files), len(files) > 1 and 'files' or 'file'))
+        if env['verbose'] == 'yes':
+            # Utter something
+            screen.write('\rPurging %d %s from cache...\n' % (len(files), len(files) > 1 and 'files' or 'file'))
         map(os.remove, files)
 
     def file_list(self):
@@ -505,22 +510,40 @@ class cache_progress:
         else:
             return [x[0] for x in file_stat[mark:]]
 
+    def convert_size(self, size_bytes):
+       if size_bytes == 0:
+           return "0 bytes"
+       size_name = ("bytes", "KB", "MB", "GB", "TB", "PB", "EB", "ZB", "YB")
+       i = int(math.floor(math.log(size_bytes, 1024)))
+       p = math.pow(1024, i)
+       s = round(size_bytes / p, 2)
+       return "%s %s" % (int(s) if i == 0 else s, size_name[i])
+
+    def get_size(self, start_path = '.'):
+        total_size = 0
+        for dirpath, dirnames, filenames in os.walk(start_path):
+            for f in filenames:
+                fp = os.path.join(dirpath, f)
+                total_size += os.path.getsize(fp)
+        return total_size
+
 def progress_finish(target, source, env):
-    global node_count
+    global node_count, progressor
     with open(node_count_fname, 'w') as f:
         f.write('%d\n' % node_count)
+    progressor.delete(progressor.file_list())
 
-if ('env' in locals() and env["progress"] == "yes"):
-    try:
-        with open(node_count_fname) as f:
-            node_count_max = int(f.readline())
-    except:
-        pass
-    cache_directory = os.environ.get("SCONS_CACHE")
-    # Simple cache pruning, attached to SCons' progress callback. Trim the
-    # cache directory to a size not larger than cache_limit.
-    cache_limit = float(os.getenv("SCONS_CACHE_LIMIT", 1024)) * 1024 * 1024
-    progress = cache_progress(cache_directory, cache_limit)
-    Progress(progress, interval = node_count_interval)
-    progress_finish_command = Command('progress_finish', [], progress_finish)
-    AlwaysBuild(progress_finish_command)
+try:
+    with open(node_count_fname) as f:
+        node_count_max = int(f.readline())
+except:
+    pass
+cache_directory = os.environ.get("SCONS_CACHE")
+# Simple cache pruning, attached to SCons' progress callback. Trim the
+# cache directory to a size not larger than cache_limit.
+cache_limit = float(os.getenv("SCONS_CACHE_LIMIT", 1024)) * 1024 * 1024
+progressor = cache_progress(cache_directory, cache_limit)
+Progress(progressor, interval = node_count_interval)
+
+progress_finish_command = Command('progress_finish', [], progress_finish)
+AlwaysBuild(progress_finish_command)

+ 1 - 0
core/SCsub

@@ -102,6 +102,7 @@ SConscript('helper/SCsub')
 
 # Build it all as a library
 lib = env.Library("core", env.core_sources)
+env.NoCache(lib)
 env.Prepend(LIBS=[lib])
 
 Export('env')

+ 1 - 0
drivers/SCsub

@@ -39,4 +39,5 @@ if env.split_drivers:
 else:
     env.add_source_files(env.drivers_sources, "*.cpp")
     lib = env.Library("drivers", env.drivers_sources)
+    env.NoCache(lib)
     env.Prepend(LIBS=[lib])

+ 1 - 0
editor/SCsub

@@ -212,6 +212,7 @@ if (env["tools"] == "yes"):
     SConscript('plugins/SCsub')
 
     lib = env.Library("editor", env.editor_sources)
+    env.NoCache(lib)
     env.Prepend(LIBS=[lib])
 
     Export('env')

+ 1 - 0
main/SCsub

@@ -10,5 +10,6 @@ Export('env')
 SConscript('tests/SCsub')
 
 lib = env.Library("main", env.main_sources)
+env.NoCache(lib)
 
 env.Prepend(LIBS=[lib])

+ 1 - 0
main/tests/SCsub

@@ -10,5 +10,6 @@ Export('env')
 # SConscript('math/SCsub');
 
 lib = env.Library("tests", env.tests_sources)
+env.NoCache(lib)
 
 env.Prepend(LIBS=[lib])

+ 6 - 1
methods.py

@@ -1418,6 +1418,7 @@ def split_lib(self, libname):
         if base != cur_base and len(list) > max_src:
             if num > 0:
                 lib = env.Library(libname + str(num), list)
+                env.NoCache(lib)
                 lib_list.append(lib)
                 list = []
             num = num + 1
@@ -1425,6 +1426,7 @@ def split_lib(self, libname):
         list.append(f)
 
     lib = env.Library(libname + str(num), list)
+    env.NoCache(lib)
     lib_list.append(lib)
 
     if len(lib_list) > 0:
@@ -1432,11 +1434,14 @@ def split_lib(self, libname):
         if os.name == 'posix' and sys.platform == 'msys':
             env.Replace(ARFLAGS=['rcsT'])
             lib = env.Library(libname + "_collated", lib_list)
+            env.NoCache(lib)
             lib_list = [lib]
 
     lib_base = []
     env.add_source_files(lib_base, "*.cpp")
-    lib_list.insert(0, env.Library(libname, lib_base))
+    lib = env.Library(libname, lib_base)
+    env.NoCache(lib)
+    lib_list.insert(0, lib)
 
     env.Prepend(LIBS=lib_list)
 

+ 1 - 0
modules/SCsub

@@ -19,5 +19,6 @@ for x in env.module_list:
     SConscript(x + "/SCsub")
 
 lib = env_modules.Library("modules", env.modules_sources)
+env.NoCache(lib)
 
 env.Prepend(LIBS=[lib])

+ 1 - 0
modules/freetype/SCsub

@@ -69,6 +69,7 @@ if (env['builtin_freetype'] != 'no'):
         env.Append(CPPPATH=["#thirdparty/libpng"])
 
     lib = env.Library("freetype_builtin", thirdparty_sources)
+    env.NoCache(lib)
     # Needs to be appended to arrive after libscene in the linker call,
     # but we don't want it to arrive *after* system libs, so manual hack
     # LIBS contains first SCons Library objects ("SCons.Node.FS.File object")

+ 2 - 2
platform/android/SCsub

@@ -143,8 +143,8 @@ manifest = manifest.replace("$$ADD_APPATTRIBUTE_CHUNKS$$", env.android_appattrib
 pp_baseout.write(manifest)
 
 
-env_android.SharedLibrary("#bin/libgodot", [android_objects], SHLIBSUFFIX=env["SHLIBSUFFIX"])
-
+lib = env_android.SharedLibrary("#bin/libgodot", [android_objects], SHLIBSUFFIX=env["SHLIBSUFFIX"])
+env_android.NoCache(lib)
 
 lib_arch_dir = ''
 if env['android_arch'] == 'armv6':

+ 1 - 0
platform/bb10/SCsub

@@ -21,3 +21,4 @@ if env['bb10_lgles_override'] == "yes":
 
 prog = None
 prog = env_bps.Program('#bin/godot', bb10_lib)
+env_bps.NoCache(prog)

+ 2 - 0
platform/iphone/SCsub

@@ -21,6 +21,7 @@ iphone_lib = [
 # env.Depends('#core/math/vector3.h', 'vector3_psp.h')
 
 #iphone_lib = env.Library('iphone', iphone_lib)
+#env.NoCache(iphone_lib)
 
 env_ios = env.Clone()
 
@@ -33,5 +34,6 @@ obj = env_ios.Object('godot_iphone.cpp')
 
 prog = None
 prog = env_ios.Program('#bin/godot', [obj] + iphone_lib)
+env_ios.NoCache(prog)
 action = "$IPHONEPATH/usr/bin/dsymutil " + File(prog)[0].path + " -o " + File(prog)[0].path + ".dSYM"
 env.AddPostAction(prog, action)

+ 2 - 1
platform/javascript/SCsub

@@ -25,4 +25,5 @@ prog = None
 
 # env_javascript.SharedLibrary("#platform/javascript/libgodot_javascript.so",[javascript_objects])
 
-env.Program('#bin/godot', javascript_objects, PROGSUFFIX=env["PROGSUFFIX"] + ".html")
+prog = env.Program('#bin/godot', javascript_objects, PROGSUFFIX=env["PROGSUFFIX"] + ".html")
+env.NoCache(prog)

+ 2 - 0
platform/osx/SCsub

@@ -14,6 +14,8 @@ files = [
 ]
 
 prog = env.Program('#bin/godot', files)
+env.NoCache(prog)
+
 if (env['target'] == "debug" or env['target'] == "release_debug"):
     # Build the .dSYM file for atos
     action = "dsymutil " + File(prog)[0].path + " -o " + File(prog)[0].path + ".dSYM"

+ 2 - 1
platform/server/SCsub

@@ -7,4 +7,5 @@ common_server = [\
     "os_server.cpp",\
 ]
 
-env.Program('#bin/godot_server', ['godot_server.cpp'] + common_server)
+prog = env.Program('#bin/godot_server', ['godot_server.cpp'] + common_server)
+env.NoCache(prog)

+ 2 - 1
platform/windows/SCsub

@@ -21,7 +21,8 @@ obj = env.RES(restarget, 'godot_res.rc')
 
 common_win.append(obj)
 
-env.Program('#bin/godot', ['godot_win.cpp'] + common_win, PROGSUFFIX=env["PROGSUFFIX"])
+prog = env.Program('#bin/godot', ['godot_win.cpp'] + common_win, PROGSUFFIX=env["PROGSUFFIX"])
+env.NoCache(prog)
 
 # Microsoft Visual Studio Project Generation
 if (env['vsproj']) == "yes":

+ 1 - 0
platform/winrt/SCsub

@@ -19,6 +19,7 @@ if "build_angle" in env and env["build_angle"]:
 	cmd = env.AlwaysBuild(env.ANGLE('libANGLE.lib', None))
 
 prog = env.Program('#bin/godot', files)
+env.NoCache(prog)
 
 if "build_angle" in env and env["build_angle"]:
 	env.Depends(prog, [cmd])

+ 2 - 1
platform/x11/SCsub

@@ -11,4 +11,5 @@ common_x11 = [
     "joystick_linux.cpp",
 ]
 
-env.Program('#bin/godot', ['godot_x11.cpp'] + common_x11)
+prog = env.Program('#bin/godot', ['godot_x11.cpp'] + common_x11)
+env.NoCache(prog)

+ 1 - 0
scene/SCsub

@@ -32,6 +32,7 @@ SConscript('io/SCsub')
 
 # Build it all as a library
 lib = env.Library("scene", env.scene_sources)
+env.NoCache(lib)
 env.Prepend(LIBS=[lib])
 
 Export('env')

+ 1 - 0
servers/SCsub

@@ -15,5 +15,6 @@ SConscript('spatial_sound/SCsub')
 SConscript('spatial_sound_2d/SCsub')
 
 lib = env.Library("servers", env.servers_sources)
+env.NoCache(lib)
 
 env.Prepend(LIBS=[lib])