diff options
Diffstat (limited to 'layout/style/generate-stylestructlist.py')
-rwxr-xr-x | layout/style/generate-stylestructlist.py | 165 |
1 files changed, 165 insertions, 0 deletions
diff --git a/layout/style/generate-stylestructlist.py b/layout/style/generate-stylestructlist.py new file mode 100755 index 000000000..346a7deae --- /dev/null +++ b/layout/style/generate-stylestructlist.py @@ -0,0 +1,165 @@ +#!/usr/bin/env python + +# 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/. + +# This script generates nsStyleStructList.h, which contains macro invocations +# that can be used for three things: +# +# 1. To generate code for each inherited style struct. +# 2. To generate code for each reset style struct. +# 3. To generate the dependency of each style struct. + +from __future__ import print_function + +import math + +NORMAL_DEP = ["Variables"] +COLOR_DEP = ["Color"] +LENGTH_DEP = ["Font", "Visibility"] + +# List of style structs and their corresponding Check callback functions, +# if any. +STYLE_STRUCTS = [("INHERITED",) + x for x in [ + # Inherited style structs. + ("Font", "CheckFontCallback", NORMAL_DEP + ["Visibility"]), + ("Color", "CheckColorCallback", NORMAL_DEP), + ("List", "nullptr", NORMAL_DEP + LENGTH_DEP), + ("Text", "CheckTextCallback", NORMAL_DEP + LENGTH_DEP + COLOR_DEP), + ("Visibility", "nullptr", NORMAL_DEP), + ("UserInterface", "nullptr", NORMAL_DEP), + ("TableBorder", "nullptr", NORMAL_DEP + LENGTH_DEP), + ("SVG", "nullptr", NORMAL_DEP + LENGTH_DEP + COLOR_DEP), + ("Variables", "CheckVariablesCallback",[]), +]] + [("RESET",) + x for x in [ + # Reset style structs. + ("Background", "nullptr", NORMAL_DEP + LENGTH_DEP + COLOR_DEP), + ("Position", "nullptr", NORMAL_DEP + LENGTH_DEP), + ("TextReset", "nullptr", NORMAL_DEP + LENGTH_DEP + COLOR_DEP), + ("Display", "nullptr", NORMAL_DEP + LENGTH_DEP), + ("Content", "nullptr", NORMAL_DEP + LENGTH_DEP), + ("UIReset", "nullptr", NORMAL_DEP), + ("Table", "nullptr", NORMAL_DEP), + ("Margin", "nullptr", NORMAL_DEP + LENGTH_DEP), + ("Padding", "nullptr", NORMAL_DEP + LENGTH_DEP), + ("Border", "nullptr", NORMAL_DEP + LENGTH_DEP + COLOR_DEP), + ("Outline", "nullptr", NORMAL_DEP + LENGTH_DEP + COLOR_DEP), + ("XUL", "nullptr", NORMAL_DEP), + ("SVGReset", "nullptr", NORMAL_DEP + LENGTH_DEP + COLOR_DEP), + ("Column", "nullptr", NORMAL_DEP + LENGTH_DEP + COLOR_DEP), + ("Effects", "nullptr", NORMAL_DEP + LENGTH_DEP + COLOR_DEP), +]] + + +# ---- Generate nsStyleStructList.h ---- + +count = len(STYLE_STRUCTS) + +# Check for problems with style struct dependencies +resolved_items = [] +# This whole loop tries to sort the style structs in topological order +# according to the dependencies. A topological order exists iff there +# are no cyclic dependencies between the style structs. It resolves one +# struct each iteration, and append the resolved one to |resolved_items|. +for i in range(count): + # This inner loop picks one style struct which does not have + # unsolved dependencies. If nothing can be picked, then we + # must have some cyclic dependencies. + for j in range(count): + _, name, _, dependencies = STYLE_STRUCTS[j] + if name in resolved_items: + continue + # Check whether all dependencies of this item have been placed + for dep in dependencies: + if dep not in resolved_items: + break + else: + resolved_items.append(name) + break + else: + import sys + print("ERROR: Cannot resolve style struct dependencies", file=sys.stderr) + print("Resolved items:", " ".join(resolved_items), file=sys.stderr) + unsolved_items = [name for _, name, _, _ in STYLE_STRUCTS + if name not in resolved_items] + print("There exist cyclic dependencies between " + + "the following structs:", " ".join(unsolved_items), file=sys.stderr) + exit(1) + +def printEntry(header, i): + print("STYLE_STRUCT_%s(%s, %s)" % STYLE_STRUCTS[i][:3], file=header) + for dep in STYLE_STRUCTS[i][3]: + print("STYLE_STRUCT_DEP(%s)" % (dep,), file=header) + print("STYLE_STRUCT_END()", file=header) + +HEADER = """/* THIS FILE IS AUTOGENERATED BY generate-stylestructlist.py - DO NOT EDIT */ + +// IWYU pragma: private, include "nsStyleStructFwd.h" + +/* + * list of structs that contain the data provided by nsStyleContext, the + * internal API for computed style data for an element + */ + +/* + * This file is intended to be used by different parts of the code, with + * the STYLE_STRUCT macro (or the STYLE_STRUCT_INHERITED and + * STYLE_STRUCT_RESET pair of macros) defined in different ways. + */ + +#ifndef STYLE_STRUCT_INHERITED +#define STYLE_STRUCT_INHERITED(name, checkdata_cb) \\ + STYLE_STRUCT(name, checkdata_cb) +#define UNDEF_STYLE_STRUCT_INHERITED +#endif + +#ifndef STYLE_STRUCT_RESET +#define STYLE_STRUCT_RESET(name, checkdata_cb) \\ + STYLE_STRUCT(name, checkdata_cb) +#define UNDEF_STYLE_STRUCT_RESET +#endif + +#ifndef STYLE_STRUCT_DEP +#define STYLE_STRUCT_DEP(dep) +#define UNDEF_STYLE_STRUCT_DEP +#endif + +#ifndef STYLE_STRUCT_END +#define STYLE_STRUCT_END() +#define UNDEF_STYLE_STRUCT_END +#endif + +// The inherited structs are listed before the Reset structs. +// nsStyleStructID assumes this is the case, and callers other than +// nsStyleStructFwd.h that want the structs in id-order just define +// STYLE_STRUCT rather than including the file twice. + +""" +FOOTER = """ +#ifdef UNDEF_STYLE_STRUCT_INHERITED +#undef STYLE_STRUCT_INHERITED +#undef UNDEF_STYLE_STRUCT_INHERITED +#endif + +#ifdef UNDEF_STYLE_STRUCT_RESET +#undef STYLE_STRUCT_RESET +#undef UNDEF_STYLE_STRUCT_RESET +#endif + +#ifdef UNDEF_STYLE_STRUCT_DEP +#undef STYLE_STRUCT_DEP +#undef UNDEF_STYLE_STRUCT_DEP +#endif + +#ifdef UNDEF_STYLE_STRUCT_END +#undef STYLE_STRUCT_END +#undef UNDEF_STYLE_STRUCT_END +#endif +""" + +def main(header): + print(HEADER, file=header) + for i in range(count): + printEntry(header, i) + print(FOOTER, file=header) |