• Home
  • Features
  • Pricing
  • Docs
  • Announcements
  • Sign In

FEniCS / ffcx / 20180168774

12 Dec 2025 09:18PM UTC coverage: 84.612% (+0.003%) from 84.609%
20180168774

Pull #808

github

schnellerhase
format
Pull Request #808: Centralise common backend routines

80 of 81 new or added lines in 7 files covered. (98.77%)

2 existing lines in 2 files now uncovered.

4168 of 4926 relevant lines covered (84.61%)

0.85 hits per line

Source File
Press 'n' to go to next uncovered line, 'b' for previous

93.98
/ffcx/codegeneration/C/form.py
1
# Copyright (C) 2009-2017 Anders Logg and Martin Sandve Alnæs
2
#
3
# This file is part of FFCx.(https://www.fenicsproject.org)
4
#
5
# SPDX-License-Identifier:    LGPL-3.0-or-later
6
#
7
# Modified by Chris Richardson and Jørgen S. Dokken 2023
8
#
9
# Note: Most of the code in this file is a direct translation from the
10
# old implementation in FFC
11
"""Generate UFC code for a form."""
12

13
from __future__ import annotations
1✔
14

15
import logging
1✔
16

17
from ffcx.codegeneration.C import form_template
1✔
18
from ffcx.codegeneration.common import integral_data, template_keys
1✔
19
from ffcx.ir.representation import FormIR
1✔
20

21
logger = logging.getLogger("ffcx")
1✔
22

23

24
def generator(ir: FormIR, options):
1✔
25
    """Generate UFCx code for a form."""
26
    logger.info("Generating code for form:")
1✔
27
    logger.info(f"--- rank: {ir.rank}")
1✔
28
    logger.info(f"--- name: {ir.name}")
1✔
29

30
    d: dict[str, int | str] = {}
1✔
31
    d["factory_name"] = ir.name
1✔
32
    d["name_from_uflfile"] = ir.name_from_uflfile
1✔
33
    d["signature"] = f'"{ir.signature}"'
1✔
34
    d["rank"] = ir.rank
1✔
35
    d["num_coefficients"] = ir.num_coefficients
1✔
36

37
    if len(ir.original_coefficient_positions) > 0:
1✔
38
        values = ", ".join(str(i) for i in ir.original_coefficient_positions)
1✔
39
        sizes = len(ir.original_coefficient_positions)
1✔
40

41
        d["original_coefficient_position_init"] = (
1✔
42
            f"int original_coefficient_position_{ir.name}[{sizes}] = {{{values}}};"
43
        )
44
        d["original_coefficient_positions"] = f"original_coefficient_position_{ir.name}"
1✔
45
    else:
46
        d["original_coefficient_position_init"] = ""
1✔
47
        d["original_coefficient_positions"] = "NULL"
1✔
48

49
    if len(ir.coefficient_names) > 0:
1✔
50
        values = ", ".join(f'"{name}"' for name in ir.coefficient_names)
1✔
51
        sizes = len(ir.coefficient_names)
1✔
52
        d["coefficient_names_init"] = (
1✔
53
            f"static const char* coefficient_names_{ir.name}[{sizes}] = {{{values}}};"
54
        )
55
        d["coefficient_names"] = f"coefficient_names_{ir.name}"
1✔
56
    else:
57
        d["coefficient_names_init"] = ""
1✔
58
        d["coefficient_names"] = "NULL"
1✔
59

60
    d["num_constants"] = ir.num_constants
1✔
61
    if ir.num_constants > 0:
1✔
62
        d["constant_ranks_init"] = (
1✔
63
            f"static const int constant_ranks_{ir.name}[{ir.num_constants}] = "
64
            f"{{{str(ir.constant_ranks)[1:-1]}}};"
65
        )
66
        d["constant_ranks"] = f"constant_ranks_{ir.name}"
1✔
67

68
        shapes = [
1✔
69
            f"static const int constant_shapes_{ir.name}_{i}[{len(shape)}] = "
70
            f"{{{str(shape)[1:-1]}}};"
71
            for i, shape in enumerate(ir.constant_shapes)
72
            if len(shape) > 0
73
        ]
74
        names = [f"constant_shapes_{ir.name}_{i}" for i in range(ir.num_constants)]
1✔
75
        shapes1 = f"static const int* constant_shapes_{ir.name}[{ir.num_constants}] = " + "{"
1✔
76
        for rank, name in zip(ir.constant_ranks, names):
1✔
77
            if rank > 0:
1✔
78
                shapes1 += f"{name},\n"
1✔
79
            else:
80
                shapes1 += "NULL,\n"
×
81
        shapes1 += "};"
1✔
82
        shapes.append(shapes1)
1✔
83

84
        d["constant_shapes_init"] = "\n".join(shapes)
1✔
85
        d["constant_shapes"] = f"constant_shapes_{ir.name}"
1✔
86
    else:
87
        d["constant_ranks_init"] = ""
1✔
88
        d["constant_ranks"] = "NULL"
1✔
89
        d["constant_shapes_init"] = ""
1✔
90
        d["constant_shapes"] = "NULL"
1✔
91

92
    if len(ir.constant_names) > 0:
1✔
93
        values = ", ".join(f'"{name}"' for name in ir.constant_names)
1✔
94
        sizes = len(ir.constant_names)
1✔
95
        d["constant_names_init"] = (
1✔
96
            f"static const char* constant_names_{ir.name}[{sizes}] = {{{values}}};"
97
        )
98
        d["constant_names"] = f"constant_names_{ir.name}"
1✔
99
    else:
100
        d["constant_names_init"] = ""
1✔
101
        d["constant_names"] = "NULL"
1✔
102

103
    if len(ir.finite_element_hashes) > 0:
1✔
104
        d["finite_element_hashes"] = f"finite_element_hashes_{ir.name}"
1✔
105
        values = ", ".join(
1✔
106
            f"UINT64_C({0 if el is None else el})" for el in ir.finite_element_hashes
107
        )
108
        sizes = len(ir.finite_element_hashes)
1✔
109
        d["finite_element_hashes_init"] = (
1✔
110
            f"uint64_t finite_element_hashes_{ir.name}[{sizes}] = {{{values}}};"
111
        )
112
    else:
113
        d["finite_element_hashes"] = "NULL"
1✔
114
        d["finite_element_hashes_init"] = ""
1✔
115

116
    integrals = integral_data(ir)
1✔
117

118
    if len(integrals.names) > 0:
1✔
119
        sizes = sum(len(domains) for domains in integrals.domains)
1✔
120
        values = ", ".join(
1✔
121
            [
122
                f"&{name}_{domain.name}"
123
                for name, domains in zip(integrals.names, integrals.domains)
124
                for domain in domains
125
            ]
126
        )
127
        d["form_integrals_init"] = (
1✔
128
            f"static ufcx_integral* form_integrals_{ir.name}[{sizes}] = {{{values}}};"
129
        )
130
        d["form_integrals"] = f"form_integrals_{ir.name}"
1✔
131
        values = ", ".join(
1✔
132
            f"{i}" for i, domains in zip(integrals.ids, integrals.domains) for _ in domains
133
        )
134
        d["form_integral_ids_init"] = f"int form_integral_ids_{ir.name}[{sizes}] = {{{values}}};"
1✔
135
        d["form_integral_ids"] = f"form_integral_ids_{ir.name}"
1✔
136
    else:
137
        d["form_integrals_init"] = ""
×
138
        d["form_integrals"] = "NULL"
×
139
        d["form_integral_ids_init"] = ""
×
UNCOV
140
        d["form_integral_ids"] = "NULL"
×
141

142
    sizes = len(integrals.offsets)
1✔
143
    values = ", ".join(str(i) for i in integrals.offsets)
1✔
144
    d["form_integral_offsets_init"] = (
1✔
145
        f"int form_integral_offsets_{ir.name}[{sizes}] = {{{values}}};"
146
    )
147

148
    # Format implementation code
149
    assert set(d.keys()) == template_keys(form_template.factory)
1✔
150
    implementation = form_template.factory.format_map(d)
1✔
151

152
    # Format declaration
153
    declaration = form_template.declaration.format(
1✔
154
        factory_name=d["factory_name"], name_from_uflfile=d["name_from_uflfile"]
155
    )
156

157
    return declaration, implementation
1✔
STATUS · Troubleshooting · Open an Issue · Sales · Support · CAREERS · ENTERPRISE · START FREE · SCHEDULE DEMO
ANNOUNCEMENTS · TWITTER · TOS & SLA · Supported CI Services · What's a CI service? · Automated Testing

© 2026 Coveralls, Inc