Skip to content

Commit 79f9dc7

Browse files
committed
doc updates
1 parent 4efce70 commit 79f9dc7

File tree

41 files changed

+1111
-1237
lines changed

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

41 files changed

+1111
-1237
lines changed

.flake8

+2
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,8 @@
22
extend-ignore =
33
# E402: module level import not at top of file
44
E402,
5+
# E741 ambiguous variable name
6+
E741,
57
# H301: one import per line
68
H301,
79
# H306: imports not in alphabetical order

.github/workflows/build.yml

+10-10
Original file line numberDiff line numberDiff line change
@@ -44,17 +44,17 @@ jobs:
4444
steps:
4545
- name: Check out repo
4646
if: always()
47-
uses: actions/checkout@v3
47+
uses: actions/checkout@v4
4848

4949
- name: Pull ccache cache
5050
if: always()
5151
id: ccache-restore
52-
uses: actions/cache/restore@v3
52+
uses: actions/cache/restore@v4
5353
with:
5454
path: /home/runner/.cache/ccache
5555
key: ccache-${{ env.BUILD_IDENTIFIER }}
5656

57-
- uses: actions/setup-python@v4
57+
- uses: actions/setup-python@v5
5858
if: always()
5959
with:
6060
python-version: ${{ matrix.py-version }}
@@ -89,7 +89,7 @@ jobs:
8989

9090
- name: Push ccache cache
9191
if: always()
92-
uses: actions/cache/save@v3
92+
uses: actions/cache/save@v4
9393
with:
9494
path: /home/runner/.cache/ccache
9595
key: ccache-${{ env.BUILD_IDENTIFIER }}
@@ -115,7 +115,7 @@ jobs:
115115
mv cython-lint.xml cython-lint-${{ env.BUILD_IDENTIFIER }}.xml
116116
117117
- name: Archive results
118-
uses: actions/upload-artifact@v3
118+
uses: actions/upload-artifact@v4
119119
if: always()
120120
with:
121121
name: Results (${{ env.BUILD_PRETTY_IDENTIFIER }})
@@ -154,20 +154,20 @@ jobs:
154154

155155
steps:
156156
- name: Check out repo
157-
uses: actions/checkout@v3
157+
uses: actions/checkout@v4
158158

159159
- name: Pull ccache cache
160160
if: always()
161161
id: ccache-restore
162-
uses: actions/cache/restore@v3
162+
uses: actions/cache/restore@v4
163163
with:
164164
path: /Users/runner/Library/Caches/ccache
165165
key: ccache-${{ runner.os }}-${{ matrix.py-version }}
166166

167167
- name: Setup GNU Fortran
168168
uses: fortran-lang/setup-fortran@v1
169169

170-
- uses: actions/setup-python@v4
170+
- uses: actions/setup-python@v5
171171
with:
172172
python-version: ${{ matrix.py-version }}
173173

@@ -203,7 +203,7 @@ jobs:
203203

204204
- name: Push ccache cache
205205
if: always()
206-
uses: actions/cache/save@v3
206+
uses: actions/cache/save@v4
207207
with:
208208
path: /Users/runner/Library/Caches/ccache
209209
key: ccache-${{ runner.os }}-${{ matrix.py-version }}
@@ -229,7 +229,7 @@ jobs:
229229
mv cython-lint.xml cython-lint-${{ runner.os }}-${{ matrix.py-version }}.xml
230230
231231
- name: Archive results
232-
uses: actions/upload-artifact@v3
232+
uses: actions/upload-artifact@v4
233233
if: always()
234234
with:
235235
name: Results ${{ github.job }}

.github/workflows/container.yml

+1-1
Original file line numberDiff line numberDiff line change
@@ -21,7 +21,7 @@ jobs:
2121
steps:
2222
- name: Check out
2323
if: always()
24-
uses: actions/checkout@v3
24+
uses: actions/checkout@v4
2525
with:
2626
fetch-depth: 0
2727

Dockerfile

+5-4
Original file line numberDiff line numberDiff line change
@@ -25,6 +25,7 @@ RUN sed -i 's/Components: main/Components: main contrib non-free/' /etc/apt/sour
2525
libmetis-dev libparmetis-dev \
2626
texlive texlive-extra-utils texlive-latex-extra ttf-staypuft dvipng cm-super \
2727
jupyter-notebook \
28+
emacs-nox vim \
2829
--no-install-recommends \
2930
&& rm -rf /var/lib/apt/lists/*
3031

@@ -36,12 +37,10 @@ WORKDIR /pynucleus
3637
RUN make prereq PIP_FLAGS=--no-cache-dir && \
3738
make prereq-extra PIP_FLAGS=--no-cache-dir && \
3839
make install && \
40+
make docs && \
3941
python -m pip install --no-cache-dir ipykernel && \
4042
rm -rf build packageTools/build base/build metisCy/build fem/build multilevelSolver/build nl/build
4143

42-
RUN echo "alias ls='ls --color=auto -FN'" >> /root/.bashrc \
43-
&& echo 'set completion-ignore-case On' >> /root/.inputrc
44-
4544
# allow running MPI as root in the container
4645
# bind MPI ranks to hwthreads
4746
ENV OMPI_MCA_hwloc_base_binding_policy=hwthread \
@@ -53,4 +52,6 @@ RUN python -m ipykernel install --name=PyNucleus
5352

5453
COPY README.container.rst /README.container.rst
5554
# hadolint ignore=SC2016
56-
RUN echo '[ ! -z "$TERM" -a -r /README.container.rst ] && cat /README.container.rst' >> /etc/bash.bashrc
55+
RUN echo '[ ! -z "$TERM" -a -r /README.container.rst ] && echo -e "\e[32m" && cat /README.container.rst && echo -e "\e[0m"' >> /etc/bash.bashrc
56+
57+
WORKDIR /root

Makefile

+2-2
Original file line numberDiff line numberDiff line change
@@ -115,8 +115,8 @@ clean_package :
115115

116116
.PHONY: docs
117117
docs :
118-
cd docs && make
119118
$(PYTHON) -m sphinx -b html docs docs/build
119+
find docs/build/_downloads -name "*.ipynb" | xargs -I {} cp {} examples
120120

121121
clean_docs :
122122
cd docs; rm -rf build
@@ -169,7 +169,7 @@ prereq:
169169
$(PYTHON) -m pip install $(PIP_FLAGS) $(PIP_INSTALL_FLAGS) scikit-sparse
170170

171171
prereq-extra:
172-
$(PYTHON) -m pip install $(PIP_FLAGS) pytest pytest-html pytest-xdist Sphinx sphinxcontrib-programoutput flake8 flake8-junit-report cython-lint
172+
$(PYTHON) -m pip install $(PIP_FLAGS) pytest pytest-html pytest-xdist Sphinx sphinxcontrib-programoutput sphinx-gallery sphinx-rtd-theme flake8 flake8-junit-report cython-lint
173173

174174
flake8:
175175
$(PYTHON) -m flake8 --output-file=flake8.txt --exit-zero drivers examples packageTools base metisCy fem multilevelSolver nl tests

README.container.rst

+8-2
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,12 @@
11

22
This is a container image for PyNucleus.
33

4-
The drivers and examples for PyNucleus can be found in /pynucleus/drivers and /pynucleus/examples
4+
The directory from which the container was launched on the host system is mapped to /root.
5+
PyNucleus is installed at /pynucleus.
6+
A copy of the drivers and examples for PyNucleus can be found in /root/drivers and /root/examples.
7+
The Jupyter notebook interface is available at https://localhost:8889 on the host.
8+
A quick way to check that everything works is to run
59

6-
The directory from which the container was launched on the host system is mapped to /user
10+
/root/drivers/runFractional.py
11+
12+
This should print some information about the solution of a fractional Laplacian problem and show several plots.

README.rst

+23-16
Original file line numberDiff line numberDiff line change
@@ -73,55 +73,62 @@ and open ``docs/build/index.html`` in your browser.
7373
Possible ways to install and use PyNucleus
7474
==================================
7575

76+
There are several ways to install and run PyNucleus:
77+
7678
* container image
7779
* Spack installation
7880
* manual installation
7981

82+
The easiest way to get up and running is probably the container image.
83+
8084

8185
Container image
8286
----------------
8387

8488
The simplest way to use PyNucleus is to pull a container image from the GitHub Container Registry.
8589
This requires an installation of either
8690

87-
* podman (https://podman.io/) and podman-compose (https://github.com/containers/podman-compose) or
88-
* Docker (https://www.docker.com/) and Docker Compose (https://docs.docker.com/compose/install/).
91+
* `podman <https://podman.io/>`_ and `podman-compose <https://github.com/containers/podman-compose?tab=readme-ov-file#installation>`_ or
92+
* `Docker <https://www.docker.com/>`_ and `Docker Compose <https://docs.docker.com/compose/install/>`_.
8993

9094
For many Linux distributions these can be installed from the package repositories.
91-
In what follows we will assume that we are using podman.
95+
In what follows we will assume that we are using `podman`.
9296
All commands for Docker should be identical up to the substitution of `podman` with `docker`.
9397

94-
For example, on Ubuntu podman can be installed with
98+
For example, on Ubuntu podman and podman-compose can be installed with
9599

96100
.. code-block:: shell
97101
98102
sudo apt-get install podman podman-compose
99103
100-
Instructions for other platforms can be found here: https://podman.io/docs/installation
104+
Instructions for other platforms can be found `here <https://podman.io/docs/installation>`_.
105+
106+
Once podman is installed, we download a copy of `compose.yaml <https://github.com/sandialabs/PyNucleus/blob/master/compose.yaml>`_ and save it to an empty directory.
107+
108+
.. warning::
109+
Please do not copy this file to your home directory and launch the container from there.
110+
The container keeps its state in the directory where it is launched from.
101111

102-
Once podman is installed, we can download a copy of https://github.com/sandialabs/PyNucleus/blob/master/compose.yaml and save it to an empty directory.
103112
In that directory we then run
104113

105114
.. code-block:: shell
106115
107-
podman compose run pynucleus
116+
podman-compose run pynucleus
117+
118+
podman will download a container image for PyNucleus and then launch a shell in the container.
119+
120+
.. note::
121+
The download of the image will only happen once, but it could be several GB in size.
108122

109-
This launches a shell on the container with PyNucleus.
110123
A simple way to test if things work is to run
111124

112125
.. code-block:: shell
113126
114127
drivers/runFractional.py
115128
116-
This should print some information about the solution of a fractional Laplacian problem and open up several plots.
117-
118-
For development using PyNucleus it can be useful to launch a Jupyter notebook server:
119-
120-
.. code-block:: shell
121-
122-
podman compose up pynucleus-jupyter
129+
This should print some information about the solution of a fractional Laplacian problem and show several plots.
123130

124-
and then open the Jupyter notebook interface at https://localhost:8889
131+
For development using PyNucleus there is the Jupyter notebook interface that is available while the container is running at https://localhost:8889 on the host system.
125132

126133

127134
Spack install

base/PyNucleus_base/LinearOperator_{SCALAR}.pxi

+66-3
Original file line numberDiff line numberDiff line change
@@ -97,6 +97,7 @@ cdef class {SCALAR_label}LinearOperator:
9797
cdef:
9898
np.ndarray[{SCALAR}_t, ndim=1] y
9999
{SCALAR}_t[::1] x_mv
100+
{SCALAR_label}TimeStepperLinearOperator tsOp
100101
try:
101102
x_mv = x
102103
y = np.zeros((self.num_rows), dtype={SCALAR})
@@ -107,6 +108,9 @@ cdef class {SCALAR_label}LinearOperator:
107108
return {SCALAR_label}Product_Linear_Operator(self, x)
108109
elif isinstance(self, {SCALAR_label}LinearOperator) and hasattr(x, 'ndim') and x.ndim == 2:
109110
return self.dotMV(x)
111+
elif isinstance(self, {SCALAR_label}TimeStepperLinearOperator) and isinstance(x, (float, int, {SCALAR})):
112+
tsOp = self
113+
return {SCALAR_label}TimeStepperLinearOperator(self, tsOp.M, tsOp.S, tsOp.facS*x, tsOp.facM*x)
110114
elif isinstance(self, {SCALAR_label}LinearOperator) and isinstance(x, (float, int, {SCALAR})):
111115
return {SCALAR_label}Multiply_Linear_Operator(self, x)
112116
elif isinstance(x, {SCALAR_label}LinearOperator) and isinstance(self, (float, int, {SCALAR})):
@@ -339,6 +343,35 @@ cdef class {SCALAR_label}TimeStepperLinearOperator({SCALAR_label}LinearOperator)
339343
assign3(y, y, 1.0, self.z, self.facM)
340344
return 0
341345

346+
cdef INDEX_t matvecTrans(self,
347+
{SCALAR}_t[::1] x,
348+
{SCALAR}_t[::1] y) except -1:
349+
if self.facS != 0.:
350+
self.S.matvecTrans(x, y)
351+
if self.facS != 1.0:
352+
scaleScalar(y, self.facS)
353+
if self.facM == 1.0:
354+
self.M.matvecTrans_no_overwrite(x, y)
355+
else:
356+
self.M.matvecTrans(x, self.z)
357+
assign3(y, y, 1.0, self.z, self.facM)
358+
return 0
359+
360+
cdef INDEX_t matvecTrans_no_overwrite(self,
361+
{SCALAR}_t[::1] x,
362+
{SCALAR}_t[::1] y) except -1:
363+
if self.facS == 1.0:
364+
self.S.matvecTrans_no_overwrite(x, y)
365+
elif self.facS != 0.:
366+
self.S.matvecTrans(x, self.z)
367+
assign3(y, y, 1.0, self.z, self.facS)
368+
if self.facM == 1.0:
369+
self.M.matvecTrans_no_overwrite(x, y)
370+
elif self.facM != 0.:
371+
self.M.matvecTrans(x, self.z)
372+
assign3(y, y, 1.0, self.z, self.facM)
373+
return 0
374+
342375
def get_diagonal(self):
343376
return (self.facM*np.array(self.M.diagonal, copy=False) +
344377
self.facS*np.array(self.S.diagonal, copy=False))
@@ -413,6 +446,22 @@ cdef class {SCALAR_label}Multiply_Linear_Operator({SCALAR_label}LinearOperator):
413446
scaleScalar(y, self.factor)
414447
return 0
415448

449+
cdef INDEX_t matvecTrans(self,
450+
{SCALAR}_t[::1] x,
451+
{SCALAR}_t[::1] y) except -1:
452+
self.A.matvecTrans(x, y)
453+
scaleScalar(y, self.factor)
454+
return 0
455+
456+
cdef INDEX_t matvecTrans_no_overwrite(self,
457+
{SCALAR}_t[::1] x,
458+
{SCALAR}_t[::1] y) except -1:
459+
if self.factor != 0.:
460+
scaleScalar(y, 1./self.factor)
461+
self.A.matvecTrans_no_overwrite(x, y)
462+
scaleScalar(y, self.factor)
463+
return 0
464+
416465
def isSparse(self):
417466
return self.A.isSparse()
418467

@@ -472,17 +521,31 @@ cdef class {SCALAR_label}Product_Linear_Operator({SCALAR_label}LinearOperator):
472521
cdef INDEX_t matvec(self,
473522
{SCALAR}_t[::1] x,
474523
{SCALAR}_t[::1] y) except -1:
475-
self.B(x, self.temporaryMemory)
476-
self.A(self.temporaryMemory, y)
524+
self.B.matvec(x, self.temporaryMemory)
525+
self.A.matvec(self.temporaryMemory, y)
477526
return 0
478527

479528
cdef INDEX_t matvec_no_overwrite(self,
480529
{SCALAR}_t[::1] x,
481530
{SCALAR}_t[::1] y) except -1:
482-
self.B(x, self.temporaryMemory)
531+
self.B.matvec(x, self.temporaryMemory)
483532
self.A.matvec_no_overwrite(self.temporaryMemory, y)
484533
return 0
485534

535+
cdef INDEX_t matvecTrans(self,
536+
{SCALAR}_t[::1] x,
537+
{SCALAR}_t[::1] y) except -1:
538+
self.A.matvecTrans(x, self.temporaryMemory)
539+
self.B.matvecTrans(self.temporaryMemory, y)
540+
return 0
541+
542+
cdef INDEX_t matvecTrans_no_overwrite(self,
543+
{SCALAR}_t[::1] x,
544+
{SCALAR}_t[::1] y) except -1:
545+
self.A.matvecTrans(x, self.temporaryMemory)
546+
self.B.matvecTrans_no_overwrite(self.temporaryMemory, y)
547+
return 0
548+
486549
cdef void _residual(self,
487550
{SCALAR}_t[::1] x,
488551
{SCALAR}_t[::1] rhs,

base/PyNucleus_base/utilsFem.py

+2
Original file line numberDiff line numberDiff line change
@@ -1376,6 +1376,8 @@ def runDriver(path, py, python=None, timeout=600, ranks=None, cacheDir='',
13761376
cache += str(ranks)
13771377
runOutput += str(ranks)
13781378
py += ['--test', '--testCache={}'.format(cache)]
1379+
if 'OVERWRITE_CACHE' in os.environ:
1380+
overwriteCache = True
13791381
if overwriteCache:
13801382
py += ['--overwriteCache']
13811383
else:

0 commit comments

Comments
 (0)