# -*- coding: utf-8 -*-

#-------------------------------------------------------------------------
# drawElements Quality Program utilities
# --------------------------------------
#
# Copyright 2015 The Android Open Source Project
#
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
# You may obtain a copy of the License at
#
#      http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS,
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
# See the License for the specific language governing permissions and
# limitations under the License.
#
#-------------------------------------------------------------------------

import os
import re
import sys
import copy
import zlib
import time
import shlex
import shutil
import fnmatch
import tarfile
import argparse
import platform
import datetime
import tempfile
import posixpath
import subprocess

from build.common import *
from build.config import *
from build.build import *

pythonExecutable = sys.executable or "python"

def die (msg):
	print msg
	sys.exit(-1)

def removeLeadingPath (path, basePath):
	# Both inputs must be normalized already
	assert os.path.normpath(path) == path
	assert os.path.normpath(basePath) == basePath
	return path[len(basePath) + 1:]

def findFile (candidates):
	for file in candidates:
		if os.path.exists(file):
			return file
	return None

def getFileList (basePath):
	allFiles	= []
	basePath	= os.path.normpath(basePath)
	for root, dirs, files in os.walk(basePath):
		for file in files:
			relPath = removeLeadingPath(os.path.normpath(os.path.join(root, file)), basePath)
			allFiles.append(relPath)
	return allFiles

def toDatetime (dateTuple):
	Y, M, D = dateTuple
	return datetime.datetime(Y, M, D)

class PackageBuildInfo:
	def __init__ (self, releaseConfig, srcBasePath, dstBasePath, tmpBasePath):
		self.releaseConfig	= releaseConfig
		self.srcBasePath	= srcBasePath
		self.dstBasePath	= dstBasePath
		self.tmpBasePath	= tmpBasePath

	def getReleaseConfig (self):
		return self.releaseConfig

	def getReleaseVersion (self):
		return self.releaseConfig.getVersion()

	def getReleaseId (self):
		# Release id is crc32(releaseConfig + release)
		return zlib.crc32(self.releaseConfig.getName() + self.releaseConfig.getVersion()) & 0xffffffff

	def getSrcBasePath (self):
		return self.srcBasePath

	def getTmpBasePath (self):
		return self.tmpBasePath

class DstFile (object):
	def __init__ (self, dstFile):
		self.dstFile = dstFile

	def makeDir (self):
		dirName = os.path.dirname(self.dstFile)
		if not os.path.exists(dirName):
			os.makedirs(dirName)

	def make (self, packageBuildInfo):
		assert False # Should not be called

class CopyFile (DstFile):
	def __init__ (self, srcFile, dstFile):
		super(CopyFile, self).__init__(dstFile)
		self.srcFile = srcFile

	def make (self, packageBuildInfo):
		self.makeDir()
		if os.path.exists(self.dstFile):
			die("%s already exists" % self.dstFile)
		shutil.copyfile(self.srcFile, self.dstFile)

class GenReleaseInfoFileTarget (DstFile):
	def __init__ (self, dstFile):
		super(GenReleaseInfoFileTarget, self).__init__(dstFile)

	def make (self, packageBuildInfo):
		self.makeDir()

		scriptPath = os.path.normpath(os.path.join(packageBuildInfo.srcBasePath, "framework", "qphelper", "gen_release_info.py"))
		execute([
				pythonExecutable,
				"-B", # no .py[co]
				scriptPath,
				"--name=%s" % packageBuildInfo.getReleaseVersion(),
				"--id=0x%08x" % packageBuildInfo.getReleaseId(),
				"--out=%s" % self.dstFile
			])

class GenCMake (DstFile):
	def __init__ (self, srcFile, dstFile, replaceVars):
		super(GenCMake, self).__init__(dstFile)
		self.srcFile		= srcFile
		self.replaceVars	= replaceVars

	def make (self, packageBuildInfo):
		self.makeDir()
		print "    GenCMake: %s" % removeLeadingPath(self.dstFile, packageBuildInfo.dstBasePath)
		src = readFile(self.srcFile)
		for var, value in self.replaceVars:
			src = re.sub('set\(%s\s+"[^"]*"' % re.escape(var),
						 'set(%s "%s"' % (var, value), src)
		writeFile(self.dstFile, src)

def createFileTargets (srcBasePath, dstBasePath, files, filters):
	usedFiles	= set() # Files that are already included by other filters
	targets		= []

	for isMatch, createFileObj in filters:
		# Build list of files that match filter
		matchingFiles = []
		for file in files:
			if not file in usedFiles and isMatch(file):
				matchingFiles.append(file)

		# Build file objects, add to used set
		for file in matchingFiles:
			usedFiles.add(file)
			targets.append(createFileObj(os.path.join(srcBasePath, file), os.path.join(dstBasePath, file)))

	return targets

# Generates multiple file targets based on filters
class FileTargetGroup:
	def __init__ (self, srcBasePath, dstBasePath, filters, srcBasePathFunc=PackageBuildInfo.getSrcBasePath):
		self.srcBasePath	= srcBasePath
		self.dstBasePath	= dstBasePath
		self.filters		= filters
		self.getSrcBasePath	= srcBasePathFunc

	def make (self, packageBuildInfo):
		fullSrcPath		= os.path.normpath(os.path.join(self.getSrcBasePath(packageBuildInfo), self.srcBasePath))
		fullDstPath		= os.path.normpath(os.path.join(packageBuildInfo.dstBasePath, self.dstBasePath))

		allFiles		= getFileList(fullSrcPath)
		targets			= createFileTargets(fullSrcPath, fullDstPath, allFiles, self.filters)

		# Make all file targets
		for file in targets:
			file.make(packageBuildInfo)

# Single file target
class SingleFileTarget:
	def __init__ (self, srcFile, dstFile, makeTarget):
		self.srcFile	= srcFile
		self.dstFile	= dstFile
		self.makeTarget	= makeTarget

	def make (self, packageBuildInfo):
		fullSrcPath		= os.path.normpath(os.path.join(packageBuildInfo.srcBasePath, self.srcFile))
		fullDstPath		= os.path.normpath(os.path.join(packageBuildInfo.dstBasePath, self.dstFile))

		target = self.makeTarget(fullSrcPath, fullDstPath)
		target.make(packageBuildInfo)

class BuildTarget:
	def __init__ (self, baseConfig, generator, targets = None):
		self.baseConfig	= baseConfig
		self.generator	= generator
		self.targets	= targets

	def make (self, packageBuildInfo):
		print "    Building %s" % self.baseConfig.getBuildDir()

		# Create config with full build dir path
		config = BuildConfig(os.path.join(packageBuildInfo.getTmpBasePath(), self.baseConfig.getBuildDir()),
							 self.baseConfig.getBuildType(),
							 self.baseConfig.getArgs(),
							 srcPath = os.path.join(packageBuildInfo.dstBasePath, "src"))

		assert not os.path.exists(config.getBuildDir())
		build(config, self.generator, self.targets)

class BuildAndroidTarget:
	def __init__ (self, dstFile):
		self.dstFile = dstFile

	def make (self, packageBuildInfo):
		print "    Building Android binary"

		buildRoot = os.path.join(packageBuildInfo.tmpBasePath, "android-build")

		assert not os.path.exists(buildRoot)
		os.makedirs(buildRoot)

		# Execute build script
		scriptPath = os.path.normpath(os.path.join(packageBuildInfo.dstBasePath, "src", "android", "scripts", "build.py"))
		execute([
				pythonExecutable,
				"-B", # no .py[co]
				scriptPath,
				"--build-root=%s" % buildRoot,
			])

		srcFile		= os.path.normpath(os.path.join(buildRoot, "package", "bin", "dEQP-debug.apk"))
		dstFile		= os.path.normpath(os.path.join(packageBuildInfo.dstBasePath, self.dstFile))

		CopyFile(srcFile, dstFile).make(packageBuildInfo)

class FetchExternalSourcesTarget:
	def __init__ (self):
		pass

	def make (self, packageBuildInfo):
		scriptPath = os.path.normpath(os.path.join(packageBuildInfo.dstBasePath, "src", "external", "fetch_sources.py"))
		execute([
				pythonExecutable,
				"-B", # no .py[co]
				scriptPath,
			])

class RemoveSourcesTarget:
	def __init__ (self):
		pass

	def make (self, packageBuildInfo):
		shutil.rmtree(os.path.join(packageBuildInfo.dstBasePath, "src"), ignore_errors=False)

class Module:
	def __init__ (self, name, targets):
		self.name		= name
		self.targets	= targets

	def make (self, packageBuildInfo):
		for target in self.targets:
			target.make(packageBuildInfo)

class ReleaseConfig:
	def __init__ (self, name, version, modules, sources = True):
		self.name			= name
		self.version		= version
		self.modules		= modules
		self.sources		= sources

	def getName (self):
		return self.name

	def getVersion (self):
		return self.version

	def getModules (self):
		return self.modules

	def packageWithSources (self):
		return self.sources

def matchIncludeExclude (includePatterns, excludePatterns, filename):
	components = os.path.normpath(filename).split(os.sep)
	for pattern in excludePatterns:
		for component in components:
			if fnmatch.fnmatch(component, pattern):
				return False

	for pattern in includePatterns:
		for component in components:
			if fnmatch.fnmatch(component, pattern):
				return True

	return False

def copyFileFilter (includePatterns, excludePatterns=[]):
	return (lambda f: matchIncludeExclude(includePatterns, excludePatterns, f),
			lambda s, d: CopyFile(s, d))

def makeFileCopyGroup (srcDir, dstDir, includePatterns, excludePatterns=[]):
	return FileTargetGroup(srcDir, dstDir, [copyFileFilter(includePatterns, excludePatterns)])

def makeTmpFileCopyGroup (srcDir, dstDir, includePatterns, excludePatterns=[]):
	return FileTargetGroup(srcDir, dstDir, [copyFileFilter(includePatterns, excludePatterns)], PackageBuildInfo.getTmpBasePath)

def makeFileCopy (srcFile, dstFile):
	return SingleFileTarget(srcFile, dstFile, lambda s, d: CopyFile(s, d))

def getReleaseFileName (configName, releaseName):
	today = datetime.date.today()
	return "dEQP-%s-%04d-%02d-%02d-%s" % (releaseName, today.year, today.month, today.day, configName)

def getTempDir ():
	dirName = os.path.join(tempfile.gettempdir(), "dEQP-Releases")
	if not os.path.exists(dirName):
		os.makedirs(dirName)
	return dirName

def makeRelease (releaseConfig):
	releaseName			= getReleaseFileName(releaseConfig.getName(), releaseConfig.getVersion())
	tmpPath				= getTempDir()
	srcBasePath			= DEQP_DIR
	dstBasePath			= os.path.join(tmpPath, releaseName)
	tmpBasePath			= os.path.join(tmpPath, releaseName + "-tmp")
	packageBuildInfo	= PackageBuildInfo(releaseConfig, srcBasePath, dstBasePath, tmpBasePath)
	dstArchiveName		= releaseName + ".tar.bz2"

	print "Creating release %s to %s" % (releaseName, tmpPath)

	# Remove old temporary dirs
	for path in [dstBasePath, tmpBasePath]:
		if os.path.exists(path):
			shutil.rmtree(path, ignore_errors=False)

	# Make all modules
	for module in releaseConfig.getModules():
		print "  Processing module %s" % module.name
		module.make(packageBuildInfo)

	# Remove sources?
	if not releaseConfig.packageWithSources():
		shutil.rmtree(os.path.join(dstBasePath, "src"), ignore_errors=False)

	# Create archive
	print "Creating %s" % dstArchiveName
	archive	= tarfile.open(dstArchiveName, 'w:bz2')
	archive.add(dstBasePath, arcname=releaseName)
	archive.close()

	# Remove tmp dirs
	for path in [dstBasePath, tmpBasePath]:
		if os.path.exists(path):
			shutil.rmtree(path, ignore_errors=False)

	print "Done!"

# Module declarations

SRC_FILE_PATTERNS	= ["*.h", "*.hpp", "*.c", "*.cpp", "*.m", "*.mm", "*.inl", "*.java", "*.aidl", "CMakeLists.txt", "LICENSE.txt", "*.cmake"]
TARGET_PATTERNS		= ["*.cmake", "*.h", "*.lib", "*.dll", "*.so", "*.txt"]

BASE = Module("Base", [
	makeFileCopy		("LICENSE",									"src/LICENSE"),
	makeFileCopy		("CMakeLists.txt",							"src/CMakeLists.txt"),
	makeFileCopyGroup	("targets",									"src/targets",							TARGET_PATTERNS),
	makeFileCopyGroup	("execserver",								"src/execserver",						SRC_FILE_PATTERNS),
	makeFileCopyGroup	("executor",								"src/executor",							SRC_FILE_PATTERNS),
	makeFileCopy		("modules/CMakeLists.txt",					"src/modules/CMakeLists.txt"),
	makeFileCopyGroup	("external",								"src/external",							["CMakeLists.txt", "*.py"]),

	# Stylesheet for displaying test logs on browser
	makeFileCopyGroup	("doc/testlog-stylesheet",					"doc/testlog-stylesheet",				["*"]),

	# Non-optional parts of framework
	makeFileCopy		("framework/CMakeLists.txt",				"src/framework/CMakeLists.txt"),
	makeFileCopyGroup	("framework/delibs",						"src/framework/delibs",					SRC_FILE_PATTERNS),
	makeFileCopyGroup	("framework/common",						"src/framework/common",					SRC_FILE_PATTERNS),
	makeFileCopyGroup	("framework/qphelper",						"src/framework/qphelper",				SRC_FILE_PATTERNS),
	makeFileCopyGroup	("framework/platform",						"src/framework/platform",				SRC_FILE_PATTERNS),
	makeFileCopyGroup	("framework/opengl",						"src/framework/opengl",					SRC_FILE_PATTERNS, ["simplereference"]),
	makeFileCopyGroup	("framework/egl",							"src/framework/egl",					SRC_FILE_PATTERNS),

	# android sources
	makeFileCopyGroup	("android/package/src",						"src/android/package/src",				SRC_FILE_PATTERNS),
	makeFileCopy		("android/package/AndroidManifest.xml",		"src/android/package/AndroidManifest.xml"),
	makeFileCopyGroup	("android/package/res",						"src/android/package/res",				["*.png", "*.xml"]),
	makeFileCopyGroup	("android/scripts",							"src/android/scripts", [
		"common.py",
		"build.py",
		"resources.py",
		"install.py",
		"launch.py",
		"debug.py"
		]),

	# Release info
	GenReleaseInfoFileTarget("src/framework/qphelper/qpReleaseInfo.inl")
])

DOCUMENTATION = Module("Documentation", [
	makeFileCopyGroup	("doc/pdf",									"doc",									["*.pdf"]),
	makeFileCopyGroup	("doc",										"doc",									["porting_layer_changes_*.txt"]),
])

GLSHARED = Module("Shared GL Tests", [
	# Optional framework components
	makeFileCopyGroup	("framework/randomshaders",					"src/framework/randomshaders",			SRC_FILE_PATTERNS),
	makeFileCopyGroup	("framework/opengl/simplereference",		"src/framework/opengl/simplereference",	SRC_FILE_PATTERNS),
	makeFileCopyGroup	("framework/referencerenderer",				"src/framework/referencerenderer",		SRC_FILE_PATTERNS),

	makeFileCopyGroup	("modules/glshared",						"src/modules/glshared",					SRC_FILE_PATTERNS),
])

GLES2 = Module("GLES2", [
	makeFileCopyGroup	("modules/gles2",							"src/modules/gles2",					SRC_FILE_PATTERNS),
	makeFileCopyGroup	("data/gles2",								"src/data/gles2",						["*.*"]),
	makeFileCopyGroup	("doc/testspecs/GLES2",						"doc/testspecs/GLES2",					["*.txt"])
])

GLES3 = Module("GLES3", [
	makeFileCopyGroup	("modules/gles3",							"src/modules/gles3",					SRC_FILE_PATTERNS),
	makeFileCopyGroup	("data/gles3",								"src/data/gles3",						["*.*"]),
	makeFileCopyGroup	("doc/testspecs/GLES3",						"doc/testspecs/GLES3",					["*.txt"])
])

GLES31 = Module("GLES31", [
	makeFileCopyGroup	("modules/gles31",							"src/modules/gles31",					SRC_FILE_PATTERNS),
	makeFileCopyGroup	("data/gles31",								"src/data/gles31",						["*.*"]),
	makeFileCopyGroup	("doc/testspecs/GLES31",					"doc/testspecs/GLES31",					["*.txt"])
])

EGL = Module("EGL", [
	makeFileCopyGroup	("modules/egl",								"src/modules/egl",						SRC_FILE_PATTERNS)
])

INTERNAL = Module("Internal", [
	makeFileCopyGroup	("modules/internal",						"src/modules/internal",					SRC_FILE_PATTERNS),
	makeFileCopyGroup	("data/internal",							"src/data/internal",					["*.*"]),
])

EXTERNAL_SRCS = Module("External sources", [
	FetchExternalSourcesTarget()
])

ANDROID_BINARIES = Module("Android Binaries", [
	BuildAndroidTarget	("bin/android/dEQP.apk"),
	makeFileCopyGroup	("targets/android",							"bin/android",							["*.bat", "*.sh"]),
])

COMMON_BUILD_ARGS	= ['-DPNG_SRC_PATH=%s' % os.path.realpath(os.path.join(DEQP_DIR, '..', 'libpng'))]
NULL_X32_CONFIG		= BuildConfig('null-x32',	'Release', ['-DDEQP_TARGET=null', '-DCMAKE_C_FLAGS=-m32', '-DCMAKE_CXX_FLAGS=-m32'] + COMMON_BUILD_ARGS)
NULL_X64_CONFIG		= BuildConfig('null-x64',	'Release', ['-DDEQP_TARGET=null', '-DCMAKE_C_FLAGS=-m64', '-DCMAKE_CXX_FLAGS=-m64'] + COMMON_BUILD_ARGS)
GLX_X32_CONFIG		= BuildConfig('glx-x32',	'Release', ['-DDEQP_TARGET=x11_glx', '-DCMAKE_C_FLAGS=-m32', '-DCMAKE_CXX_FLAGS=-m32'] + COMMON_BUILD_ARGS)
GLX_X64_CONFIG		= BuildConfig('glx-x64',	'Release', ['-DDEQP_TARGET=x11_glx', '-DCMAKE_C_FLAGS=-m64', '-DCMAKE_CXX_FLAGS=-m64'] + COMMON_BUILD_ARGS)

EXCLUDE_BUILD_FILES = ["CMakeFiles", "*.a", "*.cmake"]

LINUX_X32_COMMON_BINARIES = Module("Linux x32 Common Binaries", [
	BuildTarget			(NULL_X32_CONFIG, ANY_UNIX_GENERATOR),
	makeTmpFileCopyGroup(NULL_X32_CONFIG.getBuildDir() + "/execserver",		"bin/linux32",					["*"],	EXCLUDE_BUILD_FILES),
	makeTmpFileCopyGroup(NULL_X32_CONFIG.getBuildDir() + "/executor",		"bin/linux32",					["*"],	EXCLUDE_BUILD_FILES),
])

LINUX_X64_COMMON_BINARIES = Module("Linux x64 Common Binaries", [
	BuildTarget			(NULL_X64_CONFIG, ANY_UNIX_GENERATOR),
	makeTmpFileCopyGroup(NULL_X64_CONFIG.getBuildDir() + "/execserver",		"bin/linux64",					["*"],	EXCLUDE_BUILD_FILES),
	makeTmpFileCopyGroup(NULL_X64_CONFIG.getBuildDir() + "/executor",		"bin/linux64",					["*"],	EXCLUDE_BUILD_FILES),
])

# Special module to remove src dir, for example after binary build
REMOVE_SOURCES = Module("Remove sources from package", [
	RemoveSourcesTarget()
])

# Release configuration

ALL_MODULES		= [
	BASE,
	DOCUMENTATION,
	GLSHARED,
	GLES2,
	GLES3,
	GLES31,
	EGL,
	INTERNAL,
	EXTERNAL_SRCS,
]

ALL_BINARIES	= [
	LINUX_X64_COMMON_BINARIES,
	ANDROID_BINARIES,
]

RELEASE_CONFIGS	= {
	"src":		ALL_MODULES,
	"src-bin":	ALL_MODULES + ALL_BINARIES,
	"bin":		ALL_MODULES + ALL_BINARIES + [REMOVE_SOURCES],
}

def parseArgs ():
	parser = argparse.ArgumentParser(description = "Build release package")
	parser.add_argument("-c",
						"--config",
						dest="config",
						choices=RELEASE_CONFIGS.keys(),
						required=True,
						help="Release configuration")
	parser.add_argument("-n",
						"--name",
						dest="name",
						required=True,
						help="Package-specific name")
	parser.add_argument("-v",
						"--version",
						dest="version",
						required=True,
						help="Version code")
	return parser.parse_args()

if __name__ == "__main__":
	args	= parseArgs()
	config	= ReleaseConfig(args.name, args.version, RELEASE_CONFIGS[args.config])
	makeRelease(config)
