summaryrefslogtreecommitdiffstats
path: root/layout/style/GenerateServoCSSPropList.py
blob: 8f8badeb73b9712819177135be42db7c57dbb479 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
# This Source Code Form is subject to the terms of the Mozilla Public
# License, v. 2.0. If a copy of the MPL was not distributed with this
# file, You can obtain one at http://mozilla.org/MPL/2.0/.

import buildconfig
import mozpack.path as mozpath
import os
import runpy
import subprocess
import string
import sys

SERVO_BASE = mozpath.join(buildconfig.topsrcdir, "servo")
SERVO_PROP_BASE = mozpath.join(SERVO_BASE, "components", "style", "properties")


def generate_data(output, template):
    output.write("# THIS IS AN AUTOGENERATED FILE.  DO NOT EDIT\n\n")
    output.write(
        subprocess.check_output(
            [
                sys.executable,
                mozpath.join(SERVO_PROP_BASE, "build.py"),
                "gecko",
                "geckolib",
                template,
            ],
            universal_newlines=True,
        )
    )

    # Add all relevant files into the dependencies of the generated file.
    DEP_EXTS = [".py", ".rs", ".zip"]
    deps = set()
    for path, dirs, files in os.walk(SERVO_PROP_BASE):
        for file in files:
            if os.path.splitext(file)[1] in DEP_EXTS:
                deps.add(mozpath.join(path, file))
    return deps


def generate_header(output, data):
    data = runpy.run_path(data)["data"]

    output.write(
        """/* THIS IS AN AUTOGENERATED FILE.  DO NOT EDIT */

/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
/* vim: set ts=8 sts=2 et sw=2 tw=80: */
/* This Source Code Form is subject to the terms of the Mozilla Public
 * License, v. 2.0. If a copy of the MPL was not distributed with this
 * file, You can obtain one at https://mozilla.org/MPL/2.0/. */

#define CSS_PROP_DOMPROP_PREFIXED(name_) \\
  CSS_PROP_PUBLIC_OR_PRIVATE(Moz ## name_, name_)

#ifndef CSS_PROP_LONGHAND
#define CSS_PROP_LONGHAND(name_, id_, method_, flags_, pref_) /* nothing */
#define DEFINED_CSS_PROP_LONGHAND
#endif

#ifndef CSS_PROP_SHORTHAND
#define CSS_PROP_SHORTHAND(name_, id_, method_, flags_, pref_) /* nothing */
#define DEFINED_CSS_PROP_SHORTHAND
#endif

#ifndef CSS_PROP_ALIAS
#define CSS_PROP_ALIAS(name_, aliasid_, id_, method_, pref_) /* nothing */
#define DEFINED_CSS_PROP_ALIAS
#endif

"""
    )

    # Some flags are only used for code generation, so we don't need to
    # expose them to runtime.
    COMPILE_TIME_FLAGS = {"ExposedOnGetCS"}

    MACRO_NAMES = {
        "longhand": "CSS_PROP_LONGHAND",
        "shorthand": "CSS_PROP_SHORTHAND",
        "alias": "CSS_PROP_ALIAS",
    }
    for prop in data:
        is_internal = "Internal" in prop.flags
        pref = '"' + prop.pref + '"'
        if prop.type() == "alias":
            params = [prop.name, prop.alias_id, prop.prop_id, prop.method, pref]
        else:
            method = prop.method
            if method == "CssFloat":
                method = "CSS_PROP_PUBLIC_OR_PRIVATE(CssFloat, Float)"
            elif method.startswith("Moz"):
                method = "CSS_PROP_DOMPROP_PREFIXED({})".format(method[3:])
            flags = " | ".join(
                "CSSPropFlags::{}".format(flag)
                for flag in prop.flags
                if flag not in COMPILE_TIME_FLAGS
            )
            if not flags:
                flags = "CSSPropFlags(0)"
            params = [prop.name, prop.id, method, flags, pref]

        if is_internal:
            output.write("#ifndef CSS_PROP_LIST_EXCLUDE_INTERNAL\n")
        output.write("{}({})\n".format(MACRO_NAMES[prop.type()], ", ".join(params)))
        if is_internal:
            output.write("#endif\n")

    output.write(
        """
#ifdef DEFINED_CSS_PROP_ALIAS
#undef CSS_PROP_ALIAS
#undef DEFINED_CSS_PROP_ALIAS
#endif

#ifdef DEFINED_CSS_PROP_SHORTHAND
#undef CSS_PROP_SHORTHAND
#undef DEFINED_CSS_PROP_SHORTHAND
#endif

#ifdef DEFINED_CSS_PROP_LONGHAND
#undef CSS_PROP_LONGHAND
#undef DEFINED_CSS_PROP_LONGHAND
#endif

#undef CSS_PROP_DOMPROP_PREFIXED
"""
    )