Skip to content
Open
Show file tree
Hide file tree
Changes from 7 commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 2 additions & 0 deletions .github/workflows/core.yml
Original file line number Diff line number Diff line change
Expand Up @@ -214,6 +214,8 @@ jobs:
--extra-index-url https://download.pytorch.org/whl/cpu \
"$(echo ./firedrake-repo/dist/firedrake-*.tar.gz)[ci]"

pip install -I git+https://github.com/firedrakeproject/ufl.git@firedrakeproject:pbrubeck/hypergeometric
pip install -I git@github.com:pbrubeck/loopy.git@pbrubeck:pbrubeck/hypergeometric
firedrake-clean
pip list

Expand Down
2 changes: 1 addition & 1 deletion pyop2/compilation.py
Original file line number Diff line number Diff line change
Expand Up @@ -344,7 +344,7 @@ class LinuxGnuCompiler(Compiler):

_cflags = ("-fPIC", "-Wall", "-std=gnu11")
_cxxflags = ("-fPIC", "-Wall")
_ldflags = ("-shared",)
_ldflags = ("-shared", "-lgsl", "-lgslcblas")
Copy link
Copy Markdown
Contributor Author

@pbrubeck pbrubeck Mar 5, 2026

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@connorjward what does -shared mean? This is obviously not the correct way to add libraries, please correct me.

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think -shared means to make an .so instead of a .a file.

Regardless I think you maybe want to add this here: https://github.com/firedrakeproject/firedrake/blob/main/pyop2/global_kernel.py#L399. It might be nice to make this optional though since I don't know if we can be confident that all platforms will have this library available. However doing that would involve passing information from TSFC to PyOP2 which might be a little involved.


_optflags = ("-march=native", "-O3", "-ffast-math")
_debugflags = ("-O0", "-g")
Expand Down
31 changes: 31 additions & 0 deletions tests/firedrake/regression/test_hypergeometric_function.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,31 @@
from firedrake import *
import numpy as np
import scipy
import pytest


@pytest.mark.skipif(utils.complex_mode, reason="Complex bessel functions are not implemented.")
Comment thread
pbrubeck marked this conversation as resolved.
Outdated
def test_hypergeometric_function():
sp_hyp2f1 = scipy.special.hyp2f1
a = 1
b = 1
c = 1
mesh = UnitDiskMesh(3)
V = FunctionSpace(mesh, "CG", 1)

x, y = SpatialCoordinate(mesh)

expr = x / 10
uexact = hyp2f1(a, b, c, expr)
assert np.allclose(assemble(Function(V).interpolate(uexact)).dat.data,
sp_hyp2f1(a, b, c, assemble(Function(V).interpolate(expr)).dat.data))

expr = sqrt(x**2+y**2) / 10
uexact = hyp2f1(a, b, c, expr)
assert np.allclose(assemble(Function(V).interpolate(uexact)).dat.data,
sp_hyp2f1(a, b, c, assemble(Function(V).interpolate(expr)).dat.data))

expr = sqrt(x*x + y*y) / 10
uexact = hyp2f1(a, b, c, expr)
assert np.allclose(assemble(Function(V).interpolate(uexact)).dat.data,
sp_hyp2f1(a, b, c, assemble(Function(V).interpolate(expr)).dat.data))
6 changes: 5 additions & 1 deletion tsfc/loopy.py
Original file line number Diff line number Diff line change
Expand Up @@ -480,7 +480,11 @@ def _expression_mathfunction(expr, ctx):
else:
return p.Variable(f"{name}n")(nu_, arg_)
else:
if expr.name == "ln":
if expr.name == "hyp2f1":
assert isinstance(ctx.target, lp.target.c.CWithGNULibcTarget)
# Generate right functions calls to gsl hypergeometric function
name = "hyperg_2F1"
elif expr.name == "ln":
name = "log"
else:
name = expr.name
Expand Down
3 changes: 3 additions & 0 deletions tsfc/ufl2gem.py
Original file line number Diff line number Diff line change
Expand Up @@ -81,6 +81,9 @@ def math_function(self, o, expr):
def atan2(self, o, y, x):
return MathFunction("atan2", y, x)

def hypergeometric2_f1(self, o, a, b, c, arg):
return MathFunction(o._name, a, b, c, arg)

def bessel_i(self, o, nu, arg):
return MathFunction(o._name, nu, arg)

Expand Down
Loading