GYP(Generate Your Projects)是一个google开源的构建系统,最开始用于Chromium项目,现在一些其他的开源项目也开始使用GYP,如V8,Node.js,WebRTC等。

环境准备

配置gyp

参考: https://chromium.googlesource.com/external/gyp

git clone https://chromium.googlesource.com/external/gyp

配置depot_tools (ninja)

参考:http://commondatastorage.googleapis.com/chrome-infra-docs/flat/depot_tools/docs/html/depot_tools_tutorial.html

git clone https://chromium.googlesource.com/chromium/tools/depot_tools.git

使用gyp的例子

cpp文件

// gypTest.cpp
#include <iostream>

int main()
{
  std::cout << "hello gyp!" << std::endl;
  return 0;
}

gyp配置

# gypTest.gyp
{
  'target_defaults': {
    'default_configuration': 'Release',
    'configurations': {
      'Debug': {},
      'Release': {},
    },
  },
  'targets':[
    {
      'target_name': 'gypTest',
      'type': 'executable',
      'sources' : [
        'gypTest.cpp'
      ],
    },
  ],
}

gyp命令

gyp --depth=. -f ninja gypTest.gyp

会生成基于ninja的编译配置,ninja是一个跨平台的高效的编译工具,接下来就可以通过ninja -C out/Debug gypTest来编译了。

gyp --depth=. -f xcode gypTest.gyp

会生成xcode的工程,在Mac下就能通过xcode来打开和编译调试。

说明:

分析下chromium的gyp配置

gyp_pylib(src/tools/gyp)

这是gyp的实现部分,用python来实现,因此可以通过python导入gyp库来开发;同时gyp还提供了各个平台的脚本,可以通过脚本gyp命令(Windows下是gyp.bat)来快速生成工程配置。

gyp_chromium

这是chromium包装gyp库的python文件,通过提供了很多自定义的机制,比如可以通过-D传递gyp的变量,同时也可以通过设置环境变量来改变gyp的配置和行为。

常用用法说明:

基于 gyp_chromium 的简单包装

比如:只想以shared_library模式编译base库,可以使用如下的包装;稍加丰富这个python脚本,可以实现更多的自定义能力。

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

__author__ = 'suninf'

import os
import json
import xml.dom.minidom
import sys
import subprocess
import getopt

def getstatusoutput(cmd):
  print cmd

  args = cmd.split(" ")
  pipe = subprocess.Popen(args, stdout=subprocess.PIPE, shell=False, universal_newlines=True)
  output = "".join(pipe.stdout.readlines())
  sts = pipe.returncode
  if sts is None:
    sts = 0

  return sts, output

if __name__ == '__main__':
  common_flags = ["flag1=value1", "flag2=value2"] 

  os.environ['CHROMIUM_GYP_FILE'] = 'base/base.gyp';

  opts, args = getopt.getopt(sys.argv[1:], "", ["static", "only-ninja"])

  flags = common_flags
  flags.append("component=shared_library")

  cmd = "python build/gyp_chromium"
  for flag in flags:
    cmd = cmd + " -D " + flag

  ret,err = getstatusoutput( cmd )
  if ret==0:
    print "success"
  else:
    print "error with code: %d" % (ret)
  
  print err

关于gyp语法

gyp的详细语法也比较复杂,比如:

详细的语法还是要在使用的不断的参考和测试来掌握,gyp官方文档可以参考:https://gyp.gsrc.io/

参考