skia2/gn/gn_to_bp_utils.py
Leon Scroggins III c41a5f58b2 Generate Android Framework host-side Skia (linux)
Bug: b/118742766

Update gn_to_bp to write an Android.bp file that will build a host-side
Skia library.

Switch some methods from SK_BUILD_FOR_ANDROID to
SK_BUILD_FOR_ANDROID_FRAMEWORK.

Prior reviews were done at ag/5482397.

gn_to_bp.py:
- Run GN twice - once for android and once for linux
- Disable GPU (depends on a to-be-written host side GL target) and HEIF
  (which relies on Android hardware) on linux
  - TODO: Turn on GPU on linux
- Split sources into everywhere, android-only, and linux-only.
  It seems that Android.bp does not allow using the same cpp
  file in multiple targets.
  - note that we currently *only* divide out the sources. The cflags are
    the same (except for a couple manual ones) and include
    directories are mostly the same (again, except for manual ones).
    Android has a "gpu" include directory, which I don't expect to
    make a difference to the linux build, which isn't using GPU (yet).
- Use the same "custom empty" font manager on the host as on Android
- Write separate SkUserConfig files; one for android and one for linux.
  This allows libskia to force libraries that use it to use the right
  defines by setting export_include_dirs.
- Add extra checks to SkUserConfig.h to ensure we have only the
  appropriate SK_BUILD_FOR macro defined
- Add host_supported: true for libskia

gn_to_bp_utils.py:
- Switch SkUserConfig.h from include guards to pragma once so it is
  easier to append to the end. This matches how Android generally
  includes headers.

BUILD.gn:
- Add skia_use_fixed_gamma_text so host build can use the same SK_GAMMA
  defines as the device.

SkPreConfig.h:
- Stop making SK_BUILD_FOR_ANDROID_FRAMEWORK imply SK_BUILD_FOR_ANDROID.
  The host build needs the former defined but not the latter.

SkRegion.cpp/.h:
- Make toString() SK_BUILD_FOR_ANDROID_FRAMEWORK so it can be called on
  the host.

SkCamera.h/.cpp:
- Switch methods to SK_BUILD_FOR_ANDROID_FRAMEWORK so they can be called
  on the host.
- Make getCameraLocation*() const. They are logically const, and this
  allows removing a const_cast + TODO in hwui.

Change-Id: I771f825d06380e01c0488fd1c00df1d8a2454dc0
Reviewed-on: https://skia-review.googlesource.com/c/171231
Reviewed-by: Derek Sollenberger <djsollen@google.com>
Commit-Queue: Leon Scroggins <scroggo@google.com>
2018-11-19 17:51:32 +00:00

116 lines
4.0 KiB
Python

#!/usr/bin/env python
#
# Copyright 2018 Google Inc.
#
# Use of this source code is governed by a BSD-style license that can be
# found in the LICENSE file.
# Generate Android.bp for Skia from GN configuration.
import argparse
import json
import os
import pprint
import string
import subprocess
import tempfile
parser = argparse.ArgumentParser(description='Process some cmdline flags.')
parser.add_argument('--gn', dest='gn_cmd', default='gn')
args = parser.parse_args()
def GenerateJSONFromGN(gn_args):
gn_args = ' '.join(sorted('%s=%s' % (k,v) for (k,v) in gn_args.iteritems()))
tmp = tempfile.mkdtemp()
subprocess.check_call([args.gn_cmd, 'gen', tmp, '--args=%s' % gn_args,
'--ide=json'])
return json.load(open(os.path.join(tmp, 'project.json')))
def _strip_slash(lst):
return {str(p.lstrip('/')) for p in lst}
def GrabDependentValues(js, name, value_type, list_to_extend, exclude):
# Grab the values from other targets that $name depends on (e.g. optional
# Skia components, gms, tests, etc).
for dep in js['targets'][name]['deps']:
if 'modules' in dep:
continue # Modules require special handling -- skip for now.
if 'third_party' in dep:
continue # We've handled all third-party DEPS as static or shared_libs.
if 'none' in dep:
continue # We'll handle all cpu-specific sources manually later.
if exclude and exclude in dep:
continue
list_to_extend.update(_strip_slash(js['targets'][dep].get(value_type, [])))
GrabDependentValues(js, dep, value_type, list_to_extend, exclude)
def CleanupCFlags(cflags):
# Only use the generated flags related to warnings.
cflags = {s for s in cflags if s.startswith('-W')}
# Add additional warning suppressions so we can build
# third_party/vulkanmemoryallocator
cflags = cflags.union([
"-Wno-implicit-fallthrough",
"-Wno-missing-field-initializers",
"-Wno-thread-safety-analysis",
"-Wno-unused-variable",
])
# Add the rest of the flags we want.
cflags = cflags.union([
"-fvisibility=hidden",
"-D_FORTIFY_SOURCE=1",
"-DSKIA_DLL",
"-DSKIA_IMPLEMENTATION=1",
"-DATRACE_TAG=ATRACE_TAG_VIEW",
"-DSK_PRINT_CODEC_MESSAGES",
])
# We need to undefine FORTIFY_SOURCE before we define it. Insert it at the
# beginning after sorting.
cflags = sorted(cflags)
cflags.insert(0, "-U_FORTIFY_SOURCE")
return cflags
def CleanupCCFlags(cflags_cc):
# Only use the generated flags related to warnings.
cflags_cc = {s for s in cflags_cc if s.startswith('-W')}
# Add the rest of the flags we want.
cflags_cc.add("-fexceptions")
return cflags_cc
def _get_path_info(path, kind):
assert path == "../src"
assert kind == "abspath"
# While we want absolute paths in GN, relative paths work best here.
return "src"
def GetArchSources(opts_file):
# For architecture specific files, it's easier to just read the same source
# that GN does (opts.gni) rather than re-run GN once for each architecture.
# This .gni file we want to read is close enough to Python syntax
# that we can use execfile() if we supply definitions for GN builtins.
builtins = { 'get_path_info': _get_path_info }
defs = {}
execfile(opts_file, builtins, defs)
# Perform any string substitutions.
for arch in defs:
defs[arch] = [ p.replace('$_src', 'src') for p in defs[arch]]
return defs
def WriteUserConfig(userConfigPath, defines):
# Most defines go into SkUserConfig.h
defines.remove('NDEBUG') # Controlled by the Android build
defines.remove('SKIA_IMPLEMENTATION=1') # don't export this define.
#... and all the #defines we want to put in SkUserConfig.h.
with open(userConfigPath, 'w') as f:
print >>f, '// DO NOT MODIFY! This file is autogenerated by gn_to_bp.py.'
print >>f, '// If need to change a define, modify SkUserConfigManual.h'
print >>f, '#pragma once'
print >>f, '#include "SkUserConfigManual.h"'
for define in sorted(defines):
print >>f, '#define', define.replace('=', ' ')