Use LTO when building tagged revisions of emscripten

Adds a third mode for building with LTO: aside from enabled or disabled,
check whether the current revision of emscripten is a tagged revision,
and use LTO if so.

Also clobber working dir before and after LTO builds
diff --git a/src/build.py b/src/build.py
index 7d57c61..0c9ba52 100755
--- a/src/build.py
+++ b/src/build.py
@@ -272,6 +272,12 @@
 GCC_CLONE_DEPTH = 1000
 
 
+def ShouldUseLTO():
+    if options.use_lto == "tagged":
+        return IsTaggedRevision(GetSrcDir('emscripten'))
+    return options.use_lto == 'true'
+
+
 def CopyBinaryToArchive(binary, prefix=''):
     """All binaries are archived in the same tar file."""
     install_bin = GetInstallDir(prefix, 'bin')
@@ -524,6 +530,15 @@
         print()
 
 
+def IsTaggedRevision(src_dir):
+    try:
+        proc.check_call(['git', 'describe', '--exact-match', '--tags'],
+                        cwd=src_dir)
+    except proc.CalledProcessError:
+        return False
+    return True
+
+
 def ChromiumFetchSync(name, work_dir, git_repo,
                       checkout=RemoteBranch('master')):
     """Some Chromium projects want to use gclient for clone and
@@ -692,6 +707,12 @@
     ]
 
 
+def ClobberOneDir(work_dir):
+    if not buildbot.IsBot():
+        Remove(work_dir)
+        Mkdir(work_dir)
+
+
 def Clobber():
     # Don't automatically clobber non-bot (local) work directories
     if not buildbot.IsBot() and not options.clobber:
@@ -721,8 +742,7 @@
     else:
         dirs = work_dirs.GetAll()
     for work_dir in dirs:
-        Remove(work_dir)
-        Mkdir(work_dir)
+        ClobberOneDir(work_dir)
     # Also clobber v8
     v8_dir = os.path.join(work_dirs.GetV8(), V8_BUILD_SUBDIR)
     Remove(v8_dir)
@@ -878,9 +898,13 @@
 def LLVM():
     buildbot.Step('LLVM')
     build_dir = os.path.join(work_dirs.GetBuild(), 'llvm-out')
+    should_use_lto = ShouldUseLTO()
+    if should_use_lto:
+        # Always start and end with a clobber when using LTO
+        ClobberOneDir(build_dir)
     Mkdir(build_dir)
     cc_env = BuildEnv(build_dir, bin_subdir=True)
-    build_dylib = 'ON' if not IsWindows() and not options.use_lto else 'OFF'
+    build_dylib = 'ON' if not IsWindows() and not should_use_lto else 'OFF'
     command = CMakeCommandNative([
         GetLLVMSrcDir('llvm'),
         '-DCMAKE_CXX_FLAGS=-Wno-nonportable-include-path',
@@ -902,7 +926,7 @@
         '-DLLVM_ENABLE_TERMINFO=%d' % (not IsLinux()),
     ], build_dir)
 
-    if options.use_lto:
+    if should_use_lto:
         command.extend(['-DLLVM_ENABLE_ASSERTIONS=OFF',
                         '-DLLVM_BUILD_TESTS=OFF',
                         '-DLLVM_INCLUDE_TESTS=OFF',
@@ -931,6 +955,9 @@
                 shutil.copy2(Executable(os.path.join(install_bin, target)),
                              Executable(link))
 
+    if should_use_lto:
+        ClobberOneDir(build_dir)
+
 
 def LLVMTestDepends():
     buildbot.Step('LLVM Test Dependencies')
@@ -1056,12 +1083,16 @@
 def Binaryen():
     buildbot.Step('binaryen')
     out_dir = os.path.join(work_dirs.GetBuild(), 'binaryen-out')
+    should_use_lto = ShouldUseLTO()
+    if should_use_lto:
+        # Always start and end with a clobber when using LTO
+        ClobberOneDir(out_dir)
     Mkdir(out_dir)
     # Currently it's a bad idea to do a non-asserts build of Binaryen
     cc_env = BuildEnv(out_dir, bin_subdir=True, runtime='Debug')
 
     cmake_command = CMakeCommandNative([GetSrcDir('binaryen')], out_dir)
-    if options.use_lto:
+    if should_use_lto:
         cmake_command.append('-DBYN_ENABLE_LTO=ON')
     proc.check_call(cmake_command,
                     cwd=out_dir,
@@ -1070,6 +1101,8 @@
                     cwd=out_dir,
                     env=cc_env)
     proc.check_call(['ninja', 'install'], cwd=out_dir, env=cc_env)
+    if should_use_lto:
+        ClobberOneDir(out_dir)
 
 
 def InstallEmscripten():
@@ -1134,7 +1167,7 @@
         proc.check_call([
             sys.executable,
             os.path.join(GetInstallDir('emscripten'), 'embuilder.py'), 'build',
-            'SYSTEM'
+            'MINIMAL'
         ], env=env)
 
     except proc.CalledProcessError:
@@ -1802,8 +1835,10 @@
         '--clobber', dest='clobber', default=False, action='store_true',
         help="Delete working directories, forcing a clean build")
     parser.add_argument(
-        '--use-lto', dest='use_lto', default=False, action='store_true',
-        help='Use extra optimization for host binaries')
+        '--use-lto', dest='use_lto', default='false', action='store',
+        choices=['true', 'false', 'tagged'],
+        help='Use extra optimization for host binaries. Force to true or false,' +
+        'or use when the emscripten revision is tagged')
 
     return parser.parse_args()