diff --git a/.github/workflows/CI.yml b/.github/workflows/CI.yml
index ca0f05b997..e2586f8e27 100644
--- a/.github/workflows/CI.yml
+++ b/.github/workflows/CI.yml
@@ -47,7 +47,7 @@ jobs:
test-suites:
[
# base test: fast first test
- "testinstall",
+ "testinstall-bare",
"teststandard",
@@ -141,7 +141,7 @@ jobs:
TEST_SUITES: ${{ matrix.test-suites }}
steps:
- - uses: actions/checkout@v6
+ - uses: actions/checkout@v7
- name: "Set up Python"
uses: actions/setup-python@v6
@@ -276,7 +276,7 @@ jobs:
- name: "Gather coverage data"
run: ${{ matrix.extra }} dev/ci-gather-coverage.sh
- name: "Upload coverage data to Codecov"
- uses: codecov/codecov-action@v6
+ uses: codecov/codecov-action@v7
with:
token: ${{ secrets.CODECOV_TOKEN }}
@@ -288,7 +288,7 @@ jobs:
steps:
- name: "Send Codecov notifications"
- uses: codecov/codecov-action@v6
+ uses: codecov/codecov-action@v7
with:
token: ${{ secrets.CODECOV_TOKEN }}
run_command: send-notifications
@@ -341,7 +341,7 @@ jobs:
- name: Install cross compile dependencies
run: sudo apt-get install -q -y libgmp-dev:s390x libreadline-dev:s390x zlib1g-dev:s390x
- - uses: actions/checkout@v6
+ - uses: actions/checkout@v7
- run: ./autogen.sh
@@ -407,7 +407,7 @@ jobs:
env:
AUTOCONF_VERSION: 2.71
steps:
- - uses: actions/checkout@v6
+ - uses: actions/checkout@v7
- name: Download required GAP packages
run: |
diff --git a/.github/workflows/gapjl.yml b/.github/workflows/gapjl.yml
index 626f1a52a1..f23b79ddab 100644
--- a/.github/workflows/gapjl.yml
+++ b/.github/workflows/gapjl.yml
@@ -44,7 +44,7 @@ jobs:
steps:
- name: Checkout GAP
- uses: actions/checkout@v6
+ uses: actions/checkout@v7
with:
path: 'GAPROOT'
- name: "Set up Julia"
@@ -67,11 +67,31 @@ jobs:
- name: "Install dependencies (for macOS)"
if: runner.os == 'macOS'
run: |
- brew install autoconf zlib # gmp pkg-config
+ # - autoconf, gmp, zlib are needed by GAP's build system
+ # - coreutils provides nproc
+ # - force use of Homebrew gcc to build GAP for proper stacktrace support
+ # Homebrew installs versioned binaries such as gcc-14 and g++-14,
+ # while later scripts expect unversioned gcc and g++ in PATH.
+ brew install autoconf gmp zlib gcc@14 coreutils
+
+ # ensure gcc and g++ are available under those names (on macOS,
+ # these names are aliases for clang / clang++ out of the box)
+ shimdir="${HOME}/bin"
+ mkdir -p "${shimdir}"
+ ln -sf "$(brew --prefix)/bin/gcc-14" "${shimdir}/gcc"
+ ln -sf "$(brew --prefix)/bin/g++-14" "${shimdir}/g++"
+ echo "${shimdir}" >> "${GITHUB_PATH}"
- name: "Build GAP"
run: |
mv GAPROOT /tmp/GAPROOT
cd /tmp/GAPROOT
+ patchdir=$GAPJLPATH/.github/workflows/GAP_patches/master
+ if [ -d $patchdir ]; then
+ for f in $patchdir/*.patch; do
+ echo "Applying patch ${f}"
+ patch -p1 -d . < ${f}
+ done
+ fi
./autogen.sh
./configure --enable-Werror
make -j`nproc`
diff --git a/.github/workflows/lint.yml b/.github/workflows/lint.yml
index bbf8e68ac8..63eca8aeb6 100644
--- a/.github/workflows/lint.yml
+++ b/.github/workflows/lint.yml
@@ -15,7 +15,7 @@ jobs:
runs-on: ubuntu-slim
steps:
- name: "Check out the repository"
- uses: actions/checkout@v6
+ uses: actions/checkout@v7
- name: "Set up Python"
uses: actions/setup-python@v6
with:
diff --git a/.github/workflows/release.yml b/.github/workflows/release.yml
index 36867a212c..8c2b84a1ba 100644
--- a/.github/workflows/release.yml
+++ b/.github/workflows/release.yml
@@ -35,7 +35,7 @@ jobs:
name: "Validate release scripts"
runs-on: ubuntu-slim
steps:
- - uses: actions/checkout@v6
+ - uses: actions/checkout@v7
- name: "Set up Python"
uses: actions/setup-python@v6
@@ -57,7 +57,7 @@ jobs:
# run: python -m mypy --disallow-untyped-calls --disallow-untyped-defs dev/releases/*.py
- name: "Run tests"
- run: cd dev/releases && python -m pytest test_release_notes.py
+ run: cd dev/releases && python -m pytest
unix:
name: "Create Unix archives and data"
@@ -72,7 +72,7 @@ jobs:
# requires fetching the entire history. Therefore, we might as well do
# that here when checking out the repo, which is what setting fetch-depth
# to 0 accomplishes here.
- - uses: actions/checkout@v6
+ - uses: actions/checkout@v7
with:
fetch-depth: 0
@@ -207,7 +207,7 @@ jobs:
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
- name: "Clone the Windows installer maker scripts"
- uses: actions/checkout@v6
+ uses: actions/checkout@v7
with:
repository: gap-system/gap-windows
ref: main
diff --git a/.github/workflows/update-gh-pages.yml b/.github/workflows/update-gh-pages.yml
index e1ebb2c57b..cbafbb0093 100644
--- a/.github/workflows/update-gh-pages.yml
+++ b/.github/workflows/update-gh-pages.yml
@@ -41,7 +41,7 @@ jobs:
sudo apt-get update
sudo apt-get install --no-install-recommends "${packages[@]}"
- name: Checkout
- uses: actions/checkout@v6
+ uses: actions/checkout@v7
- name: Configure GAP
run: |
./autogen.sh && ./configure
diff --git a/.gitignore b/.gitignore
index 5d67442b54..ca50cf4952 100644
--- a/.gitignore
+++ b/.gitignore
@@ -31,6 +31,17 @@
/libgap*.dll*
/libgap*.so*
+# emscripten / wasm build outputs (etc/emscripten/build.sh and friends)
+/native-build/
+/extern/emscripten/
+/web-example/
+/packages.tar.gz
+/gap.html
+/gap.js
+/gap.wasm
+/gap.worker.js
+/gap-fs.json
+
/bin/gap*.sh
/bin/*-*/
# Compiling the `xgap` package creates the file `xgap.sh`
diff --git a/CHANGES.md b/CHANGES.md
index 6f4c6c84a9..a2e9050afa 100644
--- a/CHANGES.md
+++ b/CHANGES.md
@@ -1,5 +1,196 @@
# GAP - history of changes
+## GAP 4.16.0 (June 2026)
+
+The following gives an overview of the changes compared to the previous
+release. This list is not complete, many more internal or minor changes
+were made, but we tried to only list those changes which we think might
+affect some users directly.
+
+### New features
+
+- [#6384](https://github.com/gap-system/gap/pull/6384) Add `EnumeratorOfPartitionsSet` enumerator
+- [#6322](https://github.com/gap-system/gap/pull/6322) Add `IsGenericMatrixRep` matrix object type
+- [#6311](https://github.com/gap-system/gap/pull/6311) Add `PositionNonZeroInRow` for matrices and matrix objects
+- [#6277](https://github.com/gap-system/gap/pull/6277) Add `DirectSumGModule`
+- [#6268](https://github.com/gap-system/gap/pull/6268) Add `IsSquareMat` and `IsAntisymmetricMat`
+- [#6262](https://github.com/gap-system/gap/pull/6262) Add `UserHomeShorten` as counterpart of `UserHomeExpand`
+- [#6261](https://github.com/gap-system/gap/pull/6261) Add `WhereDepth` user preference to control depth of initial stack trace in break loops
+- [#6259](https://github.com/gap-system/gap/pull/6259) Add `IsSymmetricMatrix` (and `IsSymmetricMat` as a synonym)
+- [#6232](https://github.com/gap-system/gap/pull/6232) Add `RandomMatrix`, `RandomInvertibleMatrix`; and fix a problem with a new feature for matrix groups
+- [#6213](https://github.com/gap-system/gap/pull/6213) Add `ConformalSymplecticGroup`
+- [#5980](https://github.com/gap-system/gap/pull/5980) Add `AddMatrix`, `MultMatrix` (plus explicit left/right side variants) for in-place modification of matrices
+- [#3357](https://github.com/gap-system/gap/pull/3357) Add `FoldLeft`, `FoldLeftX`; and `ForAllX`, `ForAnyX`, `FilteredX`, `NumberX`, `PerformX` to complement `ListX`, `SetX`, `SumX`, `ProductX`
+
+### Performance improvements
+
+- [#6398](https://github.com/gap-system/gap/pull/6398) Speed up conversion from integers to finite field elements
+- [#6329](https://github.com/gap-system/gap/pull/6329) Speed up `CopySubMatrix`, `CopySubVector`, `ExtractSubMatrix`, `ExtractSubVector` for plist matrices/vectors
+- [#6289](https://github.com/gap-system/gap/pull/6289) Make the meataxe faster by using `AddMatrix`, `AddVector`, `MultMatrix`, `MultVector`
+- [#6276](https://github.com/gap-system/gap/pull/6276) Faster high-level Meataxe functions for irreducible modules (e.g. `MTX.IsomorphismModules`, `MTX.Indecomposition`, `MTX.BasisModuleEndomorphisms`, `MTX.BasisModuleHomomorphisms`)
+- [#6267](https://github.com/gap-system/gap/pull/6267) Improve conjugation test for subgroups with different orders
+- [#6265](https://github.com/gap-system/gap/pull/6265) Speed up `IsSubset` for cyclotomic domains (such as `Integers`, `PositiveIntegers`, `GaussianRationals` etc.)
+- [#6114](https://github.com/gap-system/gap/pull/6114) Enhance support for very long transversals in a permutation group by forcing down huge index steps through an intermediate subgroup
+
+### Improved and extended functionality
+
+- [#6357](https://github.com/gap-system/gap/pull/6357) Update the GAP banner to reflect the new GAP logo
+- [#6338](https://github.com/gap-system/gap/pull/6338) Improve `CosetLeadersMatFFE` documentation
+- [#6334](https://github.com/gap-system/gap/pull/6334) Translating a range by adding an integer now produces another range (instead of a plain list) when possible
+- [#6320](https://github.com/gap-system/gap/pull/6320) Add a manual section on how to write code for matrix objects
+- [#6309](https://github.com/gap-system/gap/pull/6309) Allow `CopySubVector` on plain row vectors, fix `CopySubMatrix`
+- [#6292](https://github.com/gap-system/gap/pull/6292) Document new `PackageInfo.g` fields `Dependencies.TestPackages` and `Dependencies.NeededSystemPackages`, and teach `ValidatePackageInfo` about them
+- [#6280](https://github.com/gap-system/gap/pull/6280) Implement `MultVectorRight` for lists
+- [#6257](https://github.com/gap-system/gap/pull/6257) Improve break-loop stack traces to be more consistent, provide more information and to indicate the current environment selected via `DownEnv`/`UpEnv`
+- [#6211](https://github.com/gap-system/gap/pull/6211) Improve documentation for nice monomorphisms
+- [#6183](https://github.com/gap-system/gap/pull/6183) Transfer more properties (such as `IsNaturalSL`, `InvariantQuadraticForm` etc.) when conjugating matrix groups
+
+### Removed or obsolete functionality
+
+- [#6067](https://github.com/gap-system/gap/pull/6067) Deprecate `InstallValue` for anything but plain objects (i.e., plain GAP lists, records or strings) and warn if it is done anyway
+
+### Changes related to handling of packages
+
+- [#6191](https://github.com/gap-system/gap/pull/6191) Remove unused "PC STACK" variables for from the left collectors (this breaks compatibility with polycyclic version 2.16 and older; use 2.17 or newer instead)
+
+### Changes in the documentation
+
+- [#6410](https://github.com/gap-system/gap/pull/6410) Document `OrbitStabilizer` return value
+- [#6408](https://github.com/gap-system/gap/pull/6408) Document `SemiSimpleType` field restriction
+- [#6405](https://github.com/gap-system/gap/pull/6405) Clarify `IsomorphismPcGroup` docs
+- [#6370](https://github.com/gap-system/gap/pull/6370) Improve documentation of `OnTuplesSets`, `OnSetsDisjointSets`, `OnSetsTuples`
+- [#6361](https://github.com/gap-system/gap/pull/6361) Simplify the list of `Matrix` argument variants in the manual
+- [#6348](https://github.com/gap-system/gap/pull/6348) Clarify `CompatiblePairs` documentation
+- [#6337](https://github.com/gap-system/gap/pull/6337) Clarify `IrreducibleModules` description to say 'at most' dim
+- [#6260](https://github.com/gap-system/gap/pull/6260) Document `DirectProductElement`
+- [#6220](https://github.com/gap-system/gap/pull/6220) Correct the documentation of `NewFamily`
+- [#6198](https://github.com/gap-system/gap/pull/6198) Document setter for mutable attributes
+- [#6174](https://github.com/gap-system/gap/pull/6174) Document objects with memory
+- [#6171](https://github.com/gap-system/gap/pull/6171) Improve documentation of `InverseGeneralMapping`
+- [#6169](https://github.com/gap-system/gap/pull/6169) Fix the definition of `PClassPGroup`
+- [#6162](https://github.com/gap-system/gap/pull/6162) Only show authors in `Cite`, not maintainers
+
+### Fixed bugs that could lead to incorrect results
+
+- [#6382](https://github.com/gap-system/gap/pull/6382) Fix `Irr` for natural symmetric groups when the conjugacy classes are ordered differently in the group and its character table
+- [#6358](https://github.com/gap-system/gap/pull/6358) Fix `HexSHA256` to always return 64 hex digits and not drop leading zero digits
+- [#6341](https://github.com/gap-system/gap/pull/6341) Fix return value of `PartitionsGreatestLE(0, m)` and improve its documentation
+- [#6340](https://github.com/gap-system/gap/pull/6340) Fix `MinimalGeneratingSet` for pc groups which sometimes returned incorrect (non-minimal) results
+- [#6325](https://github.com/gap-system/gap/pull/6325) Fix garbled result produced by `CosetLeadersMatFFE`
+- [#6303](https://github.com/gap-system/gap/pull/6303) Fix `CopySubVector` for GF(2) vectors to not produce invalid results for certain inputs
+- [#6253](https://github.com/gap-system/gap/pull/6253) Fix `ShortestVectors` with `"positive"` argument returning a potentially incomplete list
+- [#6245](https://github.com/gap-system/gap/pull/6245) Fix `PreImagesRepresentative` for group homomorphisms with `OnLines` action
+- [#6206](https://github.com/gap-system/gap/pull/6206) Fix two bugs in `IsomorphismPermGroupForMatrixGroup`
+- [#6203](https://github.com/gap-system/gap/pull/6203) Fix `FieldOfMatrixGroup` for certain classical matrix groups in dimension up to 2, and fix related problems with their invariant forms
+- [#6170](https://github.com/gap-system/gap/pull/6170) Fix `IsomorphismPermGroup` for trivial f. p. (sub)group
+- [#6160](https://github.com/gap-system/gap/pull/6160) Fix a bug in `RepresentativesPerfectSubgroups` that could lead to the omission of subgroups
+
+### Fixed bugs that could lead to crashes
+
+- [#6326](https://github.com/gap-system/gap/pull/6326) Fix crash in `CosetLeadersMatFFE`
+
+### Fixed bugs that could lead to unexpected errors
+
+- [#6418](https://github.com/gap-system/gap/pull/6418) Fix `RingGeneralMappingByImages` for non-SCRing
+- [#6196](https://github.com/gap-system/gap/pull/6196) Fix an inconsistency problem in `IsFinite` for matrix groups over cycl. fields.
+- [#6159](https://github.com/gap-system/gap/pull/6159) Fix a potential error message about data types when computing extensions
+
+### Other fixed bugs
+
+- [#6355](https://github.com/gap-system/gap/pull/6355) Reset the options stack after an error also when the break loop is disabled (`-T` command line option)
+- [#6218](https://github.com/gap-system/gap/pull/6218) Change `CoverageLineByLine` to produce output compatible with that produced by the `--coverage` command line option
+
+### Other changes
+
+- [#6230](https://github.com/gap-system/gap/pull/6230) Make `RestrictedMapping` of a group homomorphism use the same `Range` as the original morphism
+
+### Package distribution
+
+#### New packages redistributed with GAP
+
+- [**ClassicalMaximals**](https://gap-packages.github.io/ClassicalMaximals/) 1.1: Maximal subgroups of classical groups, by Maximilian Hauck, Max Horn, Tristan Pfersdorff, Christian Seeger, Sergio Siccha
+- [**LocalNR**](https://gap-packages.github.io/LocalNR) 2.1.0: Package of local nearrings, by Iryna Raievska, Maryna Raievska, Yaroslav Sysak
+- [**ModularGroup**](https://ag-weitze-schmithusen.github.io/ModularGroup) 2.0.2: Finite-index subgroups of (P)SL(2,Integers), by Sebastian Engelhardt, Luca Leon Junk, Hannah Wagmann, Gabriela Weitze-Schmithüsen
+- [**nofoma**](https://gap-packages.github.io/nofoma) 1.0.1: Normal forms of matrices, by Meinolf Geck, Alia Bonnet
+- [**Origami**](https://AG-Weitze-Schmithusen.github.io/Origami/) 2.0.3: Computing Veech groups of origamis, by Leo Emmerich, Sebastian Engelhardt, Simon Ertl, Luca Leon Junk, Pascal Kattler, Alexander Rogovskyy, Pascal Schumann, Andrea Thevis, Hannah Wagmann, Gabriela Weitze-Schmithüsen
+- [**PackageMaker**](https://gap-packages.github.io/PackageMaker) 1.0.1: A GAP package for creating new GAP packages, by Max Horn
+
+#### Updated packages redistributed with GAP
+
+The GAP 4.16.0 distribution contains 172 packages, of which 69 have been
+updated since GAP 4.15.1. The full list of updated packages is given below:
+
+- [**4ti2Interface**](https://homalg-project.github.io/pkg/4ti2Interface): 2024.11-01 -> 2026.05-01
+- [**Alnuth**](https://gap-packages.github.io/alnuth): 3.2.1 -> 4.0.0
+- [**ANUPQ**](https://gap-packages.github.io/anupq/): 3.3.2 -> 3.3.3
+- [**AtlasRep**](https://www.math.rwth-aachen.de/~Thomas.Breuer/atlasrep): 2.1.9 -> 2.1.11
+- [**AutoDoc**](https://gap-packages.github.io/AutoDoc): 2025.10.16 -> 2026.05.11
+- [**AutPGrp**](https://gap-packages.github.io/autpgrp/): 1.11.1 -> 1.12.0
+- [**Browse**](https://www.math.rwth-aachen.de/~Browse): 1.8.21 -> 1.8.22
+- [**CAP**](https://homalg-project.github.io/pkg/CAP): 2025.09-04 -> 2026.05-08
+- [**CaratInterface**](https://www.math.uni-bielefeld.de/~gaehler/gap/packages.php): 2.3.7 -> 2.3.9
+- [**CddInterface**](https://homalg-project.github.io/CddInterface): 2025.06.24 -> 2026.03.02
+- [**Cryst**](https://www.math.uni-bielefeld.de/~gaehler/gap/packages.php): 4.1.30 -> 4.1.31
+- [**CrystCat**](https://www.math.uni-bielefeld.de/~gaehler/gap/packages.php): 1.1.10 -> 1.1.11
+- [**curlInterface**](https://gap-packages.github.io/curlInterface/): 2.4.2 -> 2.4.3
+- [**cvec**](https://gap-packages.github.io/cvec): 2.8.4 -> 2.8.5
+- [**datastructures**](https://gap-packages.github.io/datastructures): 0.4.0 -> 0.4.1
+- [**Digraphs**](https://digraphs.github.io/Digraphs): 1.13.1 -> 1.14.0
+- [**ExamplesForHomalg**](https://homalg-project.github.io/pkg/ExamplesForHomalg): 2023.10-01 -> 2025.12-01
+- [**ferret**](https://gap-packages.github.io/ferret/): 1.0.15 -> 1.0.16
+- [**float**](https://gap-packages.github.io/float/): 1.0.9 -> 1.0.10
+- [**FORMAT**](https://gap-packages.github.io/format/): 1.4.4 -> 1.4.5
+- [**Forms**](https://gap-packages.github.io/forms): 1.2.13 -> 1.3.0
+- [**FPLSA**](https://gap-packages.github.io/FPLSA): 1.2.7 -> 1.2.8
+- [**GAPDoc**](https://www.math.rwth-aachen.de/~Frank.Luebeck/GAPDoc): 1.6.7 -> 1.6.10
+- [**Gauss**](https://homalg-project.github.io/pkg/Gauss): 2024.11-01 -> 2025.12-01
+- [**GaussForHomalg**](https://homalg-project.github.io/pkg/GaussForHomalg): 2024.08-01 -> 2026.04-01
+- [**GeneralizedMorphismsForCAP**](https://homalg-project.github.io/pkg/GeneralizedMorphismsForCAP): 2025.08-01 -> 2025.12-01
+- [**GradedModules**](https://homalg-project.github.io/pkg/GradedModules): 2024.12-01 -> 2026.04-01
+- [**GradedRingForHomalg**](https://homalg-project.github.io/pkg/GradedRingForHomalg): 2024.07-01 -> 2026.04-01
+- [**groupoids**](https://gap-packages.github.io/groupoids/): 1.79 -> 1.81
+- [**GUAVA**](https://gap-packages.github.io/guava): 3.20 -> 3.21
+- [**HAP**](https://gap-packages.github.io/hap): 1.70 -> 1.75
+- [**HAPcryst**](https://gap-packages.github.io/hapcryst/): 0.1.15 -> 0.2.0
+- [**HeLP**](https://gap-packages.github.io/HeLP): 4.0 -> 4.1
+- [**homalg**](https://homalg-project.github.io/pkg/homalg): 2024.01-01 -> 2025.12-01
+- [**HomalgToCAS**](https://homalg-project.github.io/pkg/HomalgToCAS): 2025.08-01 -> 2026.04-01
+- [**IBNP**](https://gap-packages.github.io/ibnp/): 0.17 -> 0.18
+- [**IO_ForHomalg**](https://homalg-project.github.io/pkg/IO_ForHomalg): 2023.02-04 -> 2025.12-01
+- [**json**](https://gap-packages.github.io/json/): 2.2.3 -> 2.4.0
+- [**LinearAlgebraForCAP**](https://homalg-project.github.io/pkg/LinearAlgebraForCAP): 2025.09-01 -> 2026.05-04
+- [**LocalizeRingForHomalg**](https://homalg-project.github.io/pkg/LocalizeRingForHomalg): 2023.10-01 -> 2026.05-01
+- [**lpres**](https://gap-packages.github.io/lpres): 1.1.1 -> 1.1.2
+- [**matgrp**](https://www.math.colostate.edu/~hulpke/matgrp): 0.72 -> 0.73
+- [**MatricesForHomalg**](https://homalg-project.github.io/pkg/MatricesForHomalg): 2025.09-01 -> 2026.04-01
+- [**ModIsom**](https://gap-packages.github.io/modisom/): 3.0.0 -> 3.1.0
+- [**ModulePresentationsForCAP**](https://homalg-project.github.io/pkg/ModulePresentationsForCAP): 2025.09-01 -> 2026.04-01
+- [**Modules**](https://homalg-project.github.io/pkg/Modules): 2024.12-01 -> 2026.04-01
+- [**MonoidalCategories**](https://homalg-project.github.io/pkg/MonoidalCategories): 2025.08-02 -> 2026.05-02
+- [**NConvex**](https://homalg-project.github.io/pkg/NConvex): 2024.12-01 -> 2025.12-02
+- [**NormalizInterface**](https://gap-packages.github.io/NormalizInterface): 1.4.1 -> 1.5.1
+- [**orb**](https://gap-packages.github.io/orb): 5.0.1 -> 5.1.0
+- [**Polycyclic**](https://gap-packages.github.io/polycyclic/): 2.17 -> 2.18
+- [**polymaking**](https://gap-packages.github.io/polymaking/): 0.8.7 -> 0.8.9
+- [**PrimGrp**](https://gap-packages.github.io/primgrp/): 4.0.1 -> 4.0.2
+- [**qpa**](https://gap-packages.github.io/qpa): 1.35 -> 1.37
+- [**RCWA**](https://gap-packages.github.io/rcwa/): 4.8.0 -> 4.9.0
+- [**recog**](https://gap-packages.github.io/recog): 1.4.4 -> 1.5.1
+- [**RingsForHomalg**](https://homalg-project.github.io/pkg/RingsForHomalg): 2024.11-02 -> 2026.05-01
+- [**SCO**](https://homalg-project.github.io/pkg/SCO): 2023.08-01 -> 2025.12-01
+- [**Semigroups**](https://semigroups.github.io/Semigroups): 5.5.4 -> 5.6.3
+- [**singular**](https://gap-packages.github.io/singular/): 2025.08.26 -> 2026.05.05
+- [**SmallClassNr**](https://stertooy.github.io/SmallClassNr): 1.4.2 -> 1.5.1
+- [**ToolsForHomalg**](https://homalg-project.github.io/pkg/ToolsForHomalg): 2025.05-01 -> 2026.04-01
+- [**TwistedConjugacy**](https://stertooy.github.io/TwistedConjugacy): 3.1.1 -> 3.3.2
+- [**typeset**](https://gap-packages.github.io/typeset/): 1.2.3 -> 1.2.4
+- [**utils**](https://gap-packages.github.io/utils): 0.92 -> 0.95
+- [**walrus**](https://gap-packages.github.io/walrus): 0.9991 -> 0.9992
+- [**Wedderga**](https://gap-packages.github.io/wedderga): 4.11.1 -> 4.11.3
+- [**XMod**](https://gap-packages.github.io/xmod/): 2.95 -> 2.98
+- [**ZeroMQInterface**](https://gap-packages.github.io/ZeroMQInterface/): 0.17 -> 0.18
+
+
## GAP 4.15.1 (October 2025)
The following gives an overview of the changes compared to the previous
diff --git a/CITATION b/CITATION
index 906d89e6a5..bcd784c127 100644
--- a/CITATION
+++ b/CITATION
@@ -2,23 +2,23 @@ Please use one of the following samples to cite GAP version from this installati
Text:
-[GAP] GAP – Groups, Algorithms, and Programming, Version 4.16dev,
+[GAP] GAP – Groups, Algorithms, and Programming, Version 4.17dev,
The GAP Group (this year), https://www.gap-system.org.
HTML:
[GAP]
- GAP – Groups, Algorithms, and Programming, Version 4.16dev,
+ GAP – Groups, Algorithms, and Programming, Version 4.17dev,
The GAP Group (this year),
https://www.gap-system.org.
BibXML:
-
+GAP – Groups, Algorithms,
- and Programming, Version 4.16dev
+ and Programming, Version 4.17dev
https://www.gap-system.orgthis yearGAP
@@ -28,8 +28,8 @@ BibXML:
BibTeX:
-@misc{ GAP4.16dev,
- title = {{GAP} {\textendash} {G}roups, {A}lgorithms, and {P}rogramming, {V}ersion 4.16dev},
+@misc{ GAP4.17dev,
+ title = {{GAP} {\textendash} {G}roups, {A}lgorithms, and {P}rogramming, {V}ersion 4.17dev},
organization = {The GAP {G}roup},
year = {this year},
howpublished = {\href{https://www.gap-system.org}{\texttt{https://www.gap-system.org}}},
@@ -41,7 +41,7 @@ If you are not using BibTeX, here is the bibliography entry produced
by BibTeX (in bibliography style `alpha'):
\bibitem[GAP]{GAP4}
-\emph{GAP -- Groups, Algorithms, and Programming}, Version 4.16dev,
+\emph{GAP -- Groups, Algorithms, and Programming}, Version 4.17dev,
The GAP~Group (this year), \verb+https://www.gap-system.org+.
If you have (predominantly) used one or more particular GAP packages,
diff --git a/COPYRIGHT b/COPYRIGHT
index 6a58d3bd37..b144b05166 100644
--- a/COPYRIGHT
+++ b/COPYRIGHT
@@ -14,7 +14,7 @@ You should have received a copy of the GNU General Public License
along with GAP; if not, see .
-Copyright (C) 1988-2025 by its authors, which include:
+Copyright (C) 1988-2026 by its authors, which include:
* Ákos Seress
* Alex Wegner
diff --git a/Makefile.rules b/Makefile.rules
index ffe22eb1ba..e2512739ec 100644
--- a/Makefile.rules
+++ b/Makefile.rules
@@ -24,8 +24,11 @@ default: all
########################################################################
# Developer helper targets
########################################################################
-test_release_notes:
- cd dev/releases && python3 -m pytest test_release_notes.py
+test_release_scripts:
+ cd dev/releases && python3 -m pytest
+.PHONY: test_release_scripts
+
+test_release_notes: test_release_scripts
.PHONY: test_release_notes
diff --git a/configure.ac b/configure.ac
index 1c313ffb8a..10b9b528f8 100644
--- a/configure.ac
+++ b/configure.ac
@@ -3,7 +3,7 @@ dnl Setup autoconf
dnl
AC_PREREQ([2.68])
-m4_define([gap_version], [4.16dev])
+m4_define([gap_version], [4.17dev])
m4_define([gap_releaseday], [today])
m4_define([gap_releaseyear], [this year])
@@ -727,12 +727,12 @@ for READLINE_PREFIX in ${READLINE_SEARCH_PATH} ; do
[DEFAULTS_EREADLINE],[
dnl ereadline is the name of GNU readline library on OpenBSD
READLINE_PREFIX=""
- READLINE_CPPFLAGS="-I/usr/local/include/ereadline"
+ READLINE_CPPFLAGS="-isystem /usr/local/include/ereadline"
READLINE_LDFLAGS=""
READLINE_LIBS="-lereadline"
],
[*],[
- READLINE_CPPFLAGS="-I${READLINE_PREFIX}/include"
+ READLINE_CPPFLAGS="-isystem ${READLINE_PREFIX}/include"
READLINE_LDFLAGS="-L${READLINE_PREFIX}/lib"
READLINE_LIBS="-lreadline"
]
diff --git a/dev/ci.sh b/dev/ci.sh
index e45ca39268..170a346368 100755
--- a/dev/ci.sh
+++ b/dev/ci.sh
@@ -422,6 +422,10 @@ GAPInput
;;
+ testinstall-bare)
+ $GAP $(gap_cover_arg) --bare $SRCDIR/tst/testinstall.g
+ ;;
+
*)
if [[ ! -f $SRCDIR/tst/${TEST_SUITE}.g ]]
then
diff --git a/dev/migratedoc.tex b/dev/migratedoc.tex
deleted file mode 100644
index 8e3f02270e..0000000000
--- a/dev/migratedoc.tex
+++ /dev/null
@@ -1,1141 +0,0 @@
-%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
-%%
-%W migratedoc.tex GAP documentation Thomas Breuer
-%W & Frank Celler
-%W & Martin Schoenert
-%W & Heiko Theissen
-%%
-%%
-%Y Copyright 1997, Lehrstuhl D fuer Mathematik, RWTH Aachen, Germany
-%%
-%% self-contained document with the former chapter
-%% ``Migrating to GAP 4'' of the GAP Tutorial
-%%
-\input gapmacro
-\BeginningOfBook{mig}
-\TitlePage{
- \centerline{\titlefont GAP}\bigskip
- \centerline{\secfont Release 4.5}\medskip
- \centerline{\secfont May 2012}\bigskip\bigskip
- \centerline{\titlefont Migrating to GAP 4}\vfill
- \centerline{\secfont The GAP Group}\bigskip
- \centerline{\secfont https://www.gap-system.org}
-}
-\TableOfContents
-\FrontMatter
-Copyright {\copyright} (1987-2012) for the core
-part of the {\GAP} system by the {\GAP} Group.
-
-Most parts of the {\GAP} distribution, including
-the core part of the {\GAP} system, are distributed
-under the terms of the GNU General Public License
-(see {\tt{https://www.gnu.org/licenses/gpl.html}}
-or the file {\tt GPL} in the {\tt etc} directory
-of the {\GAP} installation).
-
-More detailed information about copyright and
-licenses of parts of this distribution can be
-found in the {\GAP}~4 Reference manual
-(see {\bf Reference: Copyright and License}).
-
-{\GAP} is developed over a long time and has
-many authors and contributors. More detailed
-information can be found in the {\GAP}~4
-Reference manual (see {\bf Reference: Authors and Maintainers}).
-
-\Chapters
-
-\Chapter{Migrating to GAP 4}
-
-This chapter is intended to give users who have experience with {\GAP}~3
-some information about what has changed in {\GAP}~4.
-In particular, it informs about changed command line options
-(see~"Changed Command Line Options"),
-the new global variable `fail' (see~"Fail"),
-some functions that have changed their behaviour
-(see~"Changed Functionality") or their names
-(see~"Changed Variable Names"),
-and some conventions used for variable names (see~"Naming Conventions").
-
-Then the new concepts of {\GAP}~4 are sketched,
-first that of mutability or immutability (see~"Immutable Objects"),
-with the explanation of related changes in functions that copy objects
-(see~"Copy"),
-then the concepts of operations and method selection, which are compared
-with the use of operations records in {\GAP}~3
-(see~"Attributes vs. Record Components", "Operations Records",
-and~"Operations vs. Dispatcher Functions").
-
-More local changes affect the concepts of notions of generation
-(see~"Different Notions of Generation"),
-of parents (see~"Parents and Subgroups"),
-of homomorphisms (see~"Homomorphisms vs. General Mappings",
-"Homomorphisms vs. Factor Structures",
-and~"Isomorphisms vs. Isomorphic Structures"),
-how elements in finitely presented groups are treated
-(see~"Elements of Finitely Presented Groups"),
-how information about progress of computations can be obtained
-(see~"The Info Mechanism"),
-and how one gets information in a `break' loop
-(see~"Debugging").
-
-%Commented out: no longer provided with GAP 4.5
-%While a ``{\GAP}~3 compatibility mode'' is provided
-%(see "Compatibility Mode"),
-%its use will disable some of the new features of {\GAP}~4.
-%Also it certainly can only try to provide partial compatibility.
-
-%For a detailed explanation of the new features and concepts of {\GAP}~4,
-%see the manual ``Programming in GAP''.
-
-
-%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
-\Section{Changed Command Line Options}
-
-In {\GAP}~4, the `-l' option is used to specify the *root directory*
-(see ``GAP Root Directory'' in the {\GAP}~4 Reference Manual)
-of the {\GAP} distribution,
-which is the directory containing the `lib' and `doc' subdirectories.
-Note that in {\GAP}~3 this option was used to specify the path to the
-`lib' directory.
-
-The `-h' option of {\GAP}~3 has been removed,
-the path(s) for the documentation are deduced automatically in {\GAP}~4.
-
-The option `-g' is now used to print information only about full garbage
-collections.
-The new option `-g -g' generates information about partial
-garbage collections too.
-
-
-%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
-\Section{Fail}
-
-There is a new global variable
-
-\>`fail'{fail instead of false}
-
-in {\GAP}~4.
-It is intended as a return value of a function for the case that it
-could not perform its task.
-For example, `Inverse' returns `fail' if it is called with a singular
-matrix, and `Position' returns `fail' if the second argument is not
-contained in the list given as first argument.
-
-{\GAP}~3 handled such situations by either signalling an error,
-for example if it was asked for the inverse of a singular matrix,
-or by (mis)using `false' as return value, as in the example `Position'.
-Note that in the first example, in {\GAP}~3 it was necessary to check
-the invertibility of a matrix before one could safely ask for its
-inverse, which meant that roughly the same work was done twice.
-
-
-%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
-\Section{Changed Functionality}
-
-Some functions that were already available in {\GAP}~3 behave
-differently in {\GAP}~4. This section lists them.
-
-\>Orbit( ,)
-
-The {\GAP}~3 manual promised that would be the first entry of the
-resulting orbit. This was wrong already there in a few cases, therefore
-{\GAP}~4 does not promise anything about the ordering of points in an orbit.
-
-\>Order( )
-
-only takes the element and computes its multiplicative order.
-%Calling `Order' with two arguments is permitted only in the
-%{\GAP}~3 compatibility mode, see~"Compatibility Mode".
-(Note that it does not make sense anymore to specify a group as
-first argument w.r.t. which the order of the second argument shall
-be computed, see~"Elements of Finitely Presented Groups".)
-
-\>Position( , )
-
-If is not contained in the list then `fail' is returned
-in {\GAP}~4 (see~"Fail"), whereas `false' was returned in {\GAP}~3.
-
-
-\>PermGroupOps.ElementProperty( , [, ] )
-
-In {\GAP}~3, this function took either two or three arguments,
-the optional argument being a subgroup of that stabilizes
-in the sense that for any element in ,
-either all elements or no element in the coset ` \* ' have the
-property .
-
-The {\GAP}~4 function `ElementProperty', however,
-takes between two and four arguments,
-and the subgroup known from {\GAP}~3 has to be entered as the *fourth*
-argument *not* the third.
-(The third argument in the {\GAP}~4 function denotes a subgroup
-stabilizing in the sense that either all elements or no element
-in right cosets ` \* ' have the property .)
-
-(This discrepancy was discovered only in March~2002,
-short before the release of {\GAP}~4.3.)
-
-
-\>Print( , ... )
-
-Objects may appear on the screen in a different way,
-depending on whether they are printed by the read eval print loop
-or by an explicit call of `Print'.
-The reason is that the read eval print loop calls the operation `ViewObj'
-and not `PrintObj', whereas `Print' calls `PrintObj' for each of its
-arguments.
-This permits the installation of methods for printing objects in a short form
-in the read eval print loop while retaining `Print' to display
-the object completely.
-See also Section ``View and Print'' in the {\GAP}~4 Reference Manual.
-
-(`PrintObj' is installed as standard method `ViewObj', so it is
-not really necessary to have a `ViewObj' method for an object.)
-
-\>PrintTo( , , ... )
-
-In {\GAP}~3, `PrintTo' could be (mis)used to ``redirect'' the text
-*printed* by a function (that is, *not* only the output of a function)
-to a file by entering the function call as second argument.
-This was used mainly in order to avoid many calls of `AppendTo'.
-In {\GAP}~4, this feature has disappeared.
-One can use streams (see Chapter ``Streams'' in the {\GAP}~4 Reference Manual)
-instead in order to write files efficiently.
-
-\break
-
-%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
-\Section{Changed Variable Names}
-
-\indextt{AgGroup}
-\indextt{ApplyFunc}
-\indextt{Backtrace}
-\indextt{CharTable}
-\indextt{Denominator}
-\indextt{DepthVector}
-\indextt{Elements}
-\indextt{IsBijection}
-\indextt{IsFunc}
-\indextt{IsMat}
-\indextt{IsRec}
-\indextt{IsSet}
-\indextt{LengthWord}
-\indextt{NOfCyc}
-\indextt{Numerator}
-\indextt{RandomInvertableMat}
-\indextt{RecFields}
-\indextt{X}
-
-Some functions have changed their name without changing the
-functionality.
-A -- probably incomplete -- list follows
-\begintt
- GAP 3 GAP 4
-
- AgGroup PcGroup # (also composita)
- ApplyFunc CallFuncList
- Backtrace Where
- CharTable CharacterTable # (also composita)
- Denominator DenominatorRat
- DepthVector PositionNonZero
- Elements AsSSortedList
- IsBijection IsBijective
- IsFunc IsFunction
- IsMat IsMatrix
- IsRec IsRecord
- IsSet IsSSortedList
- LengthWord Length
- NOfCyc Conductor
- Numerator NumeratorRat
- NormedVector NormedRowVector
- Operation Action # (also composita)
- Order(G,g) Order(g)
- OrderMat Order
- OrderPerm Order
- RandomInvertableMat RandomInvertibleMat
- RecFields RecNames
- X Indeterminate
-\endtt
-
-%See Section~"Compatibility Mode" for a way to make the old names
-%available again.
-
-
-%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
-\Section{Naming Conventions}
-
-The way functions are named has been unified in {\GAP}~4.
-This might help to memorize or even guess names of library functions.
-
-If a variable name consists of several words then the first
-letter of each word is capitalized.
-
-If the first part of the name of a function is a verb then the function
-may modify its argument(s) but does not return anything,
-for example `Append' appends the list given as second argument to the
-list given as first argument.
-Otherwise the function returns an object without changing the arguments,
-for example `Concatenation' returns the concatenation of the lists
-given as arguments.
-
-If the name of a function contains the word `By' then the return value is
-thought of as built in a certain way from the parts given as arguments.
-For example, `GroupByGenerators' returns a group built from its group
-generators, and creating a group as a factor group of a given group
-by a normal subgroup can be done by taking the image of
-`NaturalHomomorphismByNormalSubgroup'
-(see also~"Homomorphisms vs. Factor Structures").
-Other examples of ```By''' functions are `GroupHomomorphismByImages' and
-`UnivariateLaurentPolynomialByCoefficients'.
-
-If the name of a function contains the word `Of' then the return value is
-thought of as information deduced from the arguments.
-Usually such functions are attributes
-(see ``Attributes'' in the {\GAP}~4 Reference Manual).
-Examples are `GeneratorsOfGroup', which returns a list of generators for
-the group entered as argument, or `DiagonalOfMat'.
-
-For the setter and tester functions of an attribute
-(see~"Attributes vs. Record Components" in this document
-and ``Attributes'' in the {\GAP}~4 Reference Manual)
-the names `Set' resp.~`Has' are available.
-
-If the name of a function ends with `NC' then there is another
-function with the same name except that the `NC' is missing.
-`NC' stands for ``no check''.
-When is called then it checks whether its arguments are valid,
-and if so then it calls .
-The functions `SubgroupNC' and `Subgroup' are a typical example.
-
-The idea is that the possibly time consuming check of the arguments
-can be omitted if one is sure that they are unnecessary.
-For example, if an algorithm produces generators of the derived subgroup
-of a group then it is guaranteed that they lie in the original group;
-`Subgroup' would check this, and `SubgroupNC' omits the check.
-
-Needless to say, all these rules are not followed slavishly,
-for example there is one operation `Zero' instead of two operations
-`ZeroOfElement' and `ZeroOfAdditiveGroup'.
-
-
-%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
-\Section{Immutable Objects}
-
-{\GAP}~4 supports ``immutable'' objects. Such objects cannot be
-changed, attempting to do so issues an error. Typically attribute
-values are immutable, and also the results of those binary arithmetic
-operations where both arguments are immutable.
-For example, `[1..100]+[1..100]' is a
-mutable list and `2 \* Immutable([1..100])' is an immutable
-list, both are equal to the (mutable) list `[2,4..200]'.
-
-There is no way to *make* an immutable object mutable, one can only
-get a mutable copy by `ShallowCopy'. The other way round,
-`MakeImmutable' makes a (mutable or immutable) object and all its
-subobjects immutable; one must be very careful to use `MakeImmutable'
-only for those objects that are really newly created, for such objects
-the advantage over `Immutable' is that no copy is made.
-
-More about immutability can be found in Sections ``Immutability'' in
-the {\GAP}~4 Tutorial and ``Mutability and Copyability'' in the {\GAP}~4
-Reference Manual.
-
-
-%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
-\Section{Copy}
-
-\indextt{StructuralCopy}
-\indextt{ShallowCopy}
-The function `Copy' of {\GAP}~3 is not supported in {\GAP}~4. This
-function was used to create a copy of its argument with
-the properties that and had no subobjects in common and
-that if two subobjects of were identical then also the
-corresponding subobjects of were identical.
-
-The possibility of having immutable objects (see~"Immutable Objects") can and
-should be used to avoid unnecessary copying.
-Namely, given an immutable object one needs to copy it only if one wants
-to get a modified object, and in such a situation usually it is
-sufficient to use `ShallowCopy', or at least one knows how deep one must
-copy in order to do the changes one has in mind.
-
-For example, suppose you have a matrix group, and you want to
-construct a list of matrices by modifying the group generators. This
-list of generators is immutable, so you call `ShallowCopy' to get a
-mutable list that contains the same matrices. If you only want to
-exchange some of them, or to append some other matrices, this shallow
-copy is already what you need. So suppose that you are interested in
-a list of matrices where some rows are also changed. For that, you
-call `ShallowCopy' for the matrices in question, and you get matrices
-whose rows can be changed. If you want to change single entries in
-some rows, `ShallowCopy' must be called to get mutable copies of these
-rows. Note that in all these situations there is no danger to change,
-i.e., to destroy the original generators of the matrix group.
-
-If one needs the facility of the `Copy' function of {\GAP}~3 to get a
-copy with the same structure then one can use the new {\GAP}~4
-function `StructuralCopy'. It returns a structural copy that has no
-*mutable* subobject in common with its argument. So if
-`StructuralCopy' is called with an immutable object then this object
-itself is returned, and if `StructuralCopy' is called with a mutable
-list of immutable objects then a shallow copy of this list is
-returned.
-
-Note that `ShallowCopy' now is an operation. So if you create your
-own type of (copyable) objects then you must define what a shallow
-copy of these objects is, and install an appropriate method.
-
-
-%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
-\Section{Attributes vs. Record Components}
-
-In {\GAP}~3, many complex objects were represented via records, for
-example all domains. Information about these objects was stored in
-components of these records. For the user, this was usually not
-relevant, since there were functions for computing information about
-the objects in question. For example, if one was interested in the
-size of a group then one could call `Size'.
-
-But since it was guaranteed that the size of a domain was stored
-as value of the component `size', it was allowed to access `.size'
-if this component was bound, and a check for this was possible via
-`IsBound( .size )'.
-
-In {\GAP}~4, only the access via functions is admissible. One reason
-is the following basic rule.
-
-*From the information that a given {\GAP}~4 object is for example a
-domain, one cannot conclude that this object has a certain
-representation.*
-
-For attributes like `Size', {\GAP}~4 provides two related functions,
-the *setter* and the *tester* of the attribute, which can be used to
-set an attribute value and to check whether the value of an attribute
-is already stored for an object (see also ``Attributes'' in the {\GAP}~4
-Reference Manual). For example, if is a domain in {\GAP}~4 then
-`HasSize( )' is `true' if the size of is already stored, and
-`false' otherwise. In the latter case, if you know that the size of
- is then you may store it by `SetSize( , )'.
-
-Besides the flexibility in the internal representation of objects,
-storing information only via function calls has also the advantage
-that {\GAP}~4 is able to draw conclusions automatically. For example,
-as soon as it is stored that a group is nilpotent, it is also stored
-that it is solvable, see Chapters ``Types of Objects'' and
-``Method Selection'' in the {\GAP}~4 Reference Manual for the details.
-
-As a consequence, you cannot put your favourite information into a
-domain by assigning it to a new component like
-`.myPrivateInfo'. Instead you can introduce a new attribute and
-then use its setter,
-see Section ``Attributes'' in the {\GAP}~4 Reference Manual.
-
-
-%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
-\Section{Different Notions of Generation}
-
-As in {\GAP}~3, a *domain* in {\GAP}~4 is a structured set.
-
-The same set can have different structures, for example a field can be
-regarded as a ring or as an algebra or vector space over a subfield.
-
-In {\GAP}~3, however, an object representing a ring did not represent
-a field, and an object representing a field did not represent a ring.
-One reason for this was that the record component `generators' was
-used to denote the appropriate generators of the domain. For a ring
-, the component `.generators' was a list of ring generators, and
-for a field , `.generators' was a list of field generators.
-
-{\GAP}~4 cleans this up,
-see ``Notions of Generation'' in the {\GAP}~4 Tutorial. It supports
-many different notions of generation, for example one can ask for
-magma generators of a group or for generators of a field as an additive
-group. A subtle but important distinction is that between generators
-of an algebra and of an algebra-with-one.
-
-So the attributes `GeneratorsOfGroup', `GeneratorsOfMagma',
-`GeneratorsOfRing', `GeneratorsOfField', `GeneratorsOfVectorSpace',
-and so on, replace the access to the `generators' component.
-
-
-%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
-\Section{Operations Records}
-
-Already in {\GAP}~3 there were several functions that were applicable
-to many different kinds of objects, for example `Size' could be
-applied to any domain, and the binary infix multiplication `*' could
-be used to multiply two matrices, an integer with a row vector, or a
-permutation with a permutation group. This was implemented as
-follows. Functions like `Size' and `*' tried to find out what
-situation was described by its arguments, and then it called a more
-specific function to compute the desired information. These more
-specific functions, let us call them *methods* as they are also called
-in {\GAP}~4, were stored in so-called *operations records* of the
-arguments.
-
-For example, every domain in {\GAP}~3 was represented as a record, and
-the operations record was stored in the record component `operations'.
-If `Size' was called for the domain then the method to compute the
-size of the domain was found as value of the `Size' component of the
-operations record.
-
-This was fine for functions taking only one argument, and in principle
-it is possible that for those functions an object stored an optimal
-method in its operations record. But in the case of more arguments
-this is not possible. In a multiplication of two objects in {\GAP}~3,
-one had to choose between the methods stored in the operations records
-of the arguments, and if for example the method stored for the left
-operand was called, this method had to handle all possible right
-operands.
-
-So operations records turned out to be not flexible enough. In
-{\GAP}~4, operations records are not supported
-%(see~"Compatibility Mode" for a possibility to use your {\GAP}~3
-%code that utilizes operations records, at least to some extent).
-A detailed description
-of the new mechanism to select methods can be found in
-Chapter ``Method Selection'' in the {\GAP}~4 Reference Manual.
-
-An important point is that the new mechanism allows {\GAP} to take the
-relation between arguments into account. So it is possible (and
-recommended) to install different methods for different relations
-between the arguments. Note that such methods need not do the
-extensive argument checking that was necessary in {\GAP}~3, because
-most of the checks are done already by the method selection mechanism.
-
-
-%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
-\Section{Operations vs. Dispatcher Functions}
-
-{\GAP}~3 functions like `Size', `CommutatorSubgroup', or
-`SylowSubgroup' did mainly call an appropriate method (see~"Operations
-Records") after they had checked their arguments. Such functions were
-called *dispatchers* in {\GAP}~3. In {\GAP}~4, many dispatchers have
-been replaced by *operations*, due to the fact that methods are no
-longer stored in operations records (see ``Method Selection'' in
-in the {\GAP}~4 Reference Manual for the details).
-
-Most dispatchers taking only one argument were treated in a special
-way in {\GAP}~3, they had the additional task of storing computed
-values and using these values in subsequent calls. For example, the
-dispatcher `Size' first checked whether the size of the argument was
-already stored, and if so then this value was returned; otherwise a
-method was called, the value returned by this method was stored in the
-argument, and then returned by `Size'.
-
-In {\GAP}~4, computed values of operations that take one argument
-(these operations are called *attributes*) are also stored, only the
-mechanism to achieve this has changed, see the sections ``Attributes''
-and ``Properties'' in the {\GAP}~4 Reference Manual.
-
-So the behaviour of `Size' is the same in {\GAP}~3 and {\GAP}~4. But
-note that in {\GAP}~4, it is not possible to access `.size',
-see~"Attributes vs. Record Components". As described in~"Operations
-Records", {\GAP}~4 does not admit ``bypassing the dispatcher'' by
-calling for example `.operations.Size'. This was done in {\GAP}~3
-often for efficiency reasons, but the method selection mechanism of
-{\GAP}~4 is fast enough to make this unnecessary.
-
-If you had written your own dispatchers and put your own methods into
-existing operations records then this code will not work in {\GAP}~4.
-See ``Creating New Objects'' and ``Method Selection'' in the {\GAP}~4
-Reference Manual for a description of how to define operations and
-to install methods.
-
-Finally, some functions in {\GAP}~3 were hidden in
-operations records, e.g., `PermGroupOps.MovedPoints'.
-These functions became proper operations in {\GAP}~4.
-
-
-%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
-\Section{Parents and Subgroups}
-
-In {\GAP}~3 there was a strict distinction between parent groups and
-subgroups.
-The use of the name ``parent'' (instead of ``supergroup'')
-was chosen to indicate that the parent of an object was more than just
-useful information.
-In fact the main reason for the introduction of parents was to provide
-a common roof for example for all groups of polycyclic words that
-belonged to the same PC-presentation, or for all subgroups of a finitely
-presented group (see~"Elements of Finitely Presented Groups").
-A subgroup was never a parent group, and it was possible to create
-subgroups only of parent groups.
-
-In {\GAP}~4 this common roof is provided already by the concept of
-*families*, see Section ``Families'' in the {\GAP}~4 Reference Manual.
-Thus it is no longer compulsory to use parent groups at all.
-On the other hand, parents *may* be used in {\GAP}~4 to provide
-information about an object, for example the normalizer of a group in its
-parent group may be stored as an attribute value.
-Note that there is no restriction on the supergroup that is set to be
-the parent,
-it is possible to create a subgroup of
-any group, this group then being the parent of the new subgroup.
-This permits for example chains of subgroups with respective parents,
-of arbitrary length.
-
-As a consequence, the `Parent' command cannot be used in {\GAP}~4 to
-test whether the two arguments of `CommutatorSubgroup' fit together,
-this is now a question that concerns the relation between the families
-of the groups. So the 2-argument version of `Parent' and the now
-meaningless function `IsParent' have been abolished.
-
-
-%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
-\Section{Homomorphisms vs. General Mappings}
-
-In {\GAP}~3 there had been a confusion between group homomorphisms and
-general mappings, as `GroupHomomorphismByImages' created only a
-general mapping that did *not* store whether it was a mapping. This
-caused expensive, unwanted, and unnecessary tests whether the mapping
-was in fact a group homomorphism. Moreover, the ``official''
-workaround to set some components of the mapping record was quite
-unwieldy.
-
-In {\GAP}~4, `GroupHomomorphismByImages' checks whether the desired
-mapping is indeed a group homomorphism; if so then this property is
-stored in the returned mapping, otherwise `fail' is returned. If you
-want to avoid the checks then you can use
-`GroupHomomorphismByImagesNC'. If you want to check whether a general
-mapping that respects the group operations is really a group
-homomorphism, you can construct it via `GroupGeneralMappingByImages'
-and then call `IsGroupHomomorphism' for it. (Note that
-`IsGroupHomomorphism' returns `true' if and only if both
-`IsGroupGeneralMapping' and `IsMapping' do, so one does in fact check
-`IsMapping' in this case.)
-
-There is *no* function `IsHomomorphism' in {\GAP}~4,
-since there are several different operations with respect to which a
-mapping can be a homomorphism.
-
-
-%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
-\Section{Homomorphisms vs. Factor Structures}
-
-If $F$ is a factor structure of $G$, with kernel $N$, complete
-information about the connection between $F$ and $G$ is provided by
-the *natural homomorphism*.
-
-In {\GAP}~3, the ``official way'' to construct this natural homomorphism
-was to create first the factor structure $F$, and then to call
-`NaturalHomomorphism' with the arguments $G$ and $F$.
-For that, the data necessary to compute the homomorphism was stored in
-$F$ when $F$ was constructed.
-
-In {\GAP}~4, factor structures are not treated in a special way,
-in particular they do not store information about a homomorphism.
-Instead, the more natural way is taken to construct the natural
-homomorphism from $G$ and $N$ by `NaturalHomomorphismByNormalSubgroup'
-if $N$ is a normal subgroup of the group $G$,
-or by `NaturalHomomorphismByIdeal' if $N$ is an ideal in the ring $G$.
-The factor $F$ can then be accessed as the image of this homomorphism,
-and of course $G$ is the preimage and $N$ is the kernel.
-
-Note that {\GAP}~4 does not guarantee anything about the representation
-of the factor $F$, it may be a permutation group or a polycyclically
-presented group or another kind of group.
-Also note that a natural homomorphism need not be surjective.
-
-A consequence of this change is that {\GAP}~4 does *not* allow you to
-construct a natural homomorphism from the groups $G$ and $F$.
-
-The other common type of homomorphism in {\GAP} 3, ``operation
-homomorphisms'', have been replaced (just a name change) by *action
-homomorphisms*, which are handled in a similar fashion. That is, an
-action homomorphism is constructed from an acting group, an action
-domain, and a function describing the operation. The permutation
-group arising by the induced action is then the image of this
-operation homomorphism.
-
-The {\GAP}~3 function `Operation' is still supported, under the name `Action',
-but from the original group and the result of `Action' it is not
-possible to construct the action homomorphism.
-
-
-%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
-\Section{Isomorphisms vs. Isomorphic Structures}
-
-In {\GAP}~3, a different representation of a group could be obtained by
-calling `AgGroup' to get an isomorphic polycyclically presented group,
-`PermGroup' to get an isomorphic permutation group, and so on.
-The returned objects stored an isomorphism in the record component
-`bijection'.
-
-For the same reason as in~"Homomorphisms vs. Factor Structures",
-{\GAP}~4 puts emphasis on the isomorphism,
-and the isomorphic object in the desired representation can be accessed
-as its image.
-So you can call `IsomorphismPcGroup' or `IsomorphismPermGroup' in order
-to get an isomorphism to a polycyclically presented group or a
-permutation group, respectively, and then call `Image' to get the
-isomorphic group.
-
-Note that the image of an action homomorphism with trivial kernel is
-also an isomorphic permutation group, but an action homomorphism need
-not be surjective, since it may be easier to define it into the full
-symmetric group.
-
-Further note that in {\GAP}~3, a usual application of isomorphisms to
-polycyclically presented groups was to utilize the usually more
-effective algorithms for solvable groups. However, the new concept of
-polycyclic generating systems in {\GAP}~4 makes it possible to apply
-these algorithms to arbitrary solvable groups, independent of the
-representation. For example, {\GAP}~4 can handle polycyclic
-generating systems of solvable permutation groups. So in many cases,
-a change of the representation for efficiency reasons may be not
-necessary any longer.
-
-In general `IsomorphismFpGroup' will define a presentation on generators
-chosen by the algorithm. The corresponding elements of the original
-group can be obtained by the command
-\begintt
-gens:=List(GeneratorsOfGroup(Image(isofp)),i->PreImagesRepresentative(isofp,i));
-\endtt
-If a presentation in the given generators is needed, the command
-`IsomorphismFpGroupByGenerators(, )' will produce one.
-
-
-%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
-\Section{Elements of Finitely Presented Groups}
-
-Strictly speaking, {\GAP}~3 did not support elements of finitely
-presented groups. Instead, the ``words in abstract generators'' of
-the underlying free groups were (mis)used. This caused problems
-whenever calculations with elements were involved, the most obvious
-ones being wrong results of element comparisons. Also functions
-that should in principle work for any group were not applicable to
-finitely presented groups. In effect, a finitely presented group had
-to be treated in a special way in {\GAP}~3.
-
-{\GAP}~4 distinguishes free groups and their elements from finitely
-presented groups and their elements. Comparing two elements of a
-finitely presented group will yield either the correct result or no
-result at all.
-
-Note that in {\GAP}~4, the arithmetic and comparison operations for
-group elements do not depend on a context provided by a group that
-contains the elements. In particular, in {\GAP}~4 it is not
-meaningful to call `Order( , )' for a group and an element
-.
-
-%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
-\Section{Polynomials}
-
-In {\GAP}~3, polynomials were defined over a field. So a polynomial over
-`GF(3)' was different from a polynomial over `GF(9)', even if the
-coefficients were exactly the same.
-
-{\GAP}~4 defines polynomials only over a characteristic. This makes it
-possible for example to multiply a polynomial over `GF(3)' with a polynomial
-over `GF(9)' without the need to convert the former to the larger field.
-
-However it has an effect on the result of `DefaultRing' for polynomials:
-In {\GAP}~3 the default ring for a polynomial was the polynomial ring of the
-field over which the polynomial was defined. In {\GAP}~4 no field is
-associated, so (to avoid having to define the algebraic closure as the only
-other sensible alternative) the default ring of a polynomial is the
-`DefaultRing' of its coefficients.
-
-This has an effect on `Factors': If no ring is given, a polynomial is
-factorized over its `DefaultRing' and so `Factors()'
-might return different results.
-
-To be safe from this problem, if you are not working over prime fields,
-rather call `Factors(,)' with the appropriate polynomial ring
-and change your code accordingly.
-
-%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
-\Section{The Info Mechanism}
-
-Sometimes it is useful to get information about the progress of a
-calculation.
-Many {\GAP} functions contain statements to display such information
-under certain conditions.
-
-In {\GAP}~3, these statements were calls to functions such as
-`InfoGroup1' or `InfoGroup2', and if the user assigned `Print' to
-these variables then this had the effect to switch on the printing of
-information.
-`InfoGroup2' was used for more detailed information than `InfoGroup1'.
-One could switch off the printing again by assigning `Ignore' to the
-variables, and `Ignore' was also the default value.
-
-{\GAP}~4 uses one function `Info' for the same purpose,
-which is a function that takes as first argument an *info class* such as
-`InfoGroup', as second argument an *info level*, and the print statements
-as remaining arguments.
-The level of an info class is set to by calling
-`SetInfoLevel( , )'.
-An `Info' statement is printed only if its second argument is smaller than
-or equal to the current info level.
-For example,
-\beginexample
-gap> test:= function( obj )
-> Info( InfoGroup, 2, "This is useful, isn't it?" );
-> return obj;
-> end;;
-gap> test( 1 );
-1
-gap> SetInfoLevel( InfoGroup, 2 );
-gap> test( 1 );
-#I This is useful, isn't it?
-1
-\endexample
-
-As in {\GAP}~3, if an info statement is ignored then its arguments are
-not evaluated.
-
-
-%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
-\Section{Debugging}
-
-\indextt{Backtrace}
-\indextt{DownEnv}
-\indextt{Where}
-If {\GAP}~4 runs into an error or is interrupted,
-it enters a break loop.
-The command `Where( )', which replaces `Backtrace' of {\GAP}~3,
-can be used to display lines of information about the current
-function call stack.
-
-As in {\GAP}~3, access is only possible to the variables of the current
-level in the function stack,
-but in {\GAP}~4 the function `DownEnv', with a positive or negative
-integer as argument, permits one to step down or up in the
-stack.
-
-When interrupting, the first line printed by `Where' actually may be
-one level higher, as the following example shows
-\begintt
-gap> OnBreak := function() Where(0); end;; # eliminate back-tracing on
-gap> # entry to break loop
-gap> test:= function( n )
-> if n > 3 then Error( "!\n" ); fi; test( n+1 ); end;;
-gap> test( 1 );
-Error, !
-Entering break read-eval-print loop ...
-you can 'quit;' to quit to outer loop, or
-you can 'return;' to continue
-brk> Where();
- called from
-test( n + 1 ); called from
-test( n + 1 ); called from
-test( n + 1 ); called from
-( ) called from read-eval-loop
-brk> n;
-4
-brk> DownEnv();
-brk> n;
-3
-brk> Where();
- called from
-test( n + 1 ); called from
-test( n + 1 ); called from
-( ) called from read-eval-loop
-brk> DownEnv( 2 );
-brk> n;
-1
-brk> Where();
- called from
-( ) called from read-eval-loop
-brk> DownEnv( -2 );
-brk> n;
-3
-brk> quit;
-gap> OnBreak := Where;; # restore OnBreak to its default value
-\endtt
-
-For purposes of debugging, it can be helpful sometimes, to see what
-information is stored within an object. In {\GAP}~3 this was possible using
-`RecFields' because the objects in question were represented via records.
-For component objects, {\GAP}~4 permits the same by
-`NamesOfComponents(
+A technical remark:Run_In_GGMBI
+
+
+
+In order to avoid infinite recursions when constructing nice monomorphisms,
+the global option Run_In_GGMBI is set to true in certain
+situations.
+The value of this option is checked in methods for the operations
+ and
+.
+
<#Include Label="IsHandledByNiceMonomorphism">
<#Include Label="NiceMonomorphism">
<#Include Label="NiceObject">
diff --git a/doc/ref/helpintf.xml b/doc/ref/helpintf.xml
index 6ed9b9be27..3daccf2773 100644
--- a/doc/ref/helpintf.xml
+++ b/doc/ref/helpintf.xml
@@ -164,7 +164,7 @@ gap> stream := InputTextFile( file );;
This must return a text string or list of text lines which contains the
chapter headers of the book info.bookname.
-ShowSection( info )
+ShowSections( info )
This must return a text string or list of text lines which contains the
section (and chapter) headers of the book info.bookname.
diff --git a/doc/ref/language.xml b/doc/ref/language.xml
index cab355969b..b0e03199ff 100644
--- a/doc/ref/language.xml
+++ b/doc/ref/language.xml
@@ -715,11 +715,9 @@ gap> xx := 15;
15
gap> MakeReadOnlyGlobal("xx");
gap> xx := 16;
-Variable: 'xx' is read only
-not in any function
-Entering break read-eval-print loop ...
-you can 'quit;' to quit to outer loop, or
-you can 'return;' after making it writable to continue
+Error, Variable: 'xx' is read only
+not in any function at *stdin*:3
+you can enter 'quit;' to quit to outer loop
brk> quit;
gap> IsReadOnlyGlobal("xx");
true
@@ -1563,11 +1561,12 @@ gap> f2:= function( x ) return f1( x ); end;;
gap> f2( 4 );
value: 4
Error, Function Calls: must return a value
+Stack trace:
*[1] f1( x )
@ *stdin*:2
( )
called from read-eval loop at *stdin*:3
-type 'quit;' to quit to outer loop
+you can enter 'quit;' to quit to outer loop
brk>
]]>
diff --git a/doc/ref/methsel.xml b/doc/ref/methsel.xml
index 1ce2674710..5e88dabef2 100644
--- a/doc/ref/methsel.xml
+++ b/doc/ref/methsel.xml
@@ -127,13 +127,13 @@ gap> XCons(IsFullTransformationMonoid,4);
Error, no method found! For debugging hints type ?Recovery from NoMethodFound
Error, no 1st choice method found for `XCons' on 2 arguments
called from read-eval loop at *stdin*:8
-type 'quit;' to quit to outer loop
+you can enter 'quit;' to quit to outer loop
brk> quit;
gap> XCons(IsNilpotentGroup,4);
Error, no method found! For debugging hints type ?Recovery from NoMethodFound
Error, no 1st choice method found for `XCons' on 2 arguments
called from read-eval loop at *stdin*:8
-type 'quit;' to quit to outer loop
+you can enter 'quit;' to quit to outer loop
brk>
]]>
diff --git a/doc/ref/mloop.xml b/doc/ref/mloop.xml
index b39f2f50e8..8b9aef83fa 100644
--- a/doc/ref/mloop.xml
+++ b/doc/ref/mloop.xml
@@ -478,7 +478,7 @@ indicate that you are in a break loop.
gap> 1/0;
Error, Rational operations: must not be zero
not in any function at *stdin*:2
-type 'quit;' to quit to outer loop
+you can enter 'quit;' to quit to outer loop
]]>
If errors occur within a break loop &GAP; enters another break loop at a
@@ -487,8 +487,8 @@ If errors occur within a break loop &GAP; enters another break loop at a
1/0;
Error, Rational operations: must not be zero
-not in any function at *stdin*:2
-type 'quit;' to quit to outer loop
+not in any function at *errin*:1
+you can enter 'quit;' to quit to outer loop
brk_2>
]]>
@@ -537,25 +537,11 @@ purpose of this function.
returnreturn from break loop
The other way to leave a break loop is to return from a break loop.
-To do this you type return; or return obj;.
If the break loop was entered because you interrupted &GAP;,
then you can continue by typing return;.
-If the break loop was entered due to an error,
-you may have to modify the value of a variable before typing return;
-(see the example for ) or you may have to
-return an object obj
-(by typing: return obj;) to continue the computation;
-in any case, the message printed on entering the break loop will
-tell you which of these alternatives is possible.
-For example, if the break loop was entered because a variable had no
-assigned value, the value to be returned is often a value that this
-variable should have to continue the computation.
-
- return 9; # we had tried to enter the divisor 9 but typed 0 ...
-1/9
-gap>
-]]>
+If the break loop was entered due to an error, this option may or may not
+be available, depending on the kind of error. The message printed on entering
+the break loop will tell you whether this possible.
@@ -581,9 +567,8 @@ function( ) ... end
gap> Error("!\n");
Error, !
Hello
-Entering break read-eval-print loop ...
-you can 'quit;' to quit to outer loop, or
-you can 'return;' to continue
+you can enter 'quit;' to quit to outer loop, or
+you can enter 'return;' to continue
brk> quit;
]]>
@@ -606,8 +591,7 @@ emitted at level 1
Note that for break loops entered by a call to ,
-the lines after Entering break read-eval-print loop ...
-and before the brk> prompt can also be customised,
+the lines just before the brk> prompt can also be customised,
namely by redefining .
ErrorNoTraceBack
@@ -648,10 +632,10 @@ Here is a somewhat trivial demonstration of the use of
ErrorNoTraceBack("Gidday!", " How's", " it", " going?\n");
-Error, Gidday! How's it going?
-Entering break read-eval-print loop ...
-you can 'quit;' to quit to outer loop, or
-you can 'return;' to continue
+Error,
+Gidday! How's it going?
+you can enter 'quit;' to quit to outer loop, or
+you can enter 'return;' to continue
brk> quit;
]]>
@@ -661,9 +645,8 @@ Now we call with the same arguments to show the difference.
gap> Error("Gidday!", " How's", " it", " going?\n");
Error, Gidday! How's it going?
Hello
-Entering break read-eval-print loop ...
-you can 'quit;' to quit to outer loop, or
-you can 'return;' to continue
+you can enter 'quit;' to quit to outer loop, or
+you can enter 'return;' to continue
brk> quit;
]]>
@@ -685,17 +668,16 @@ gap> OnBreak := Where;;
Break loop message
When a break loop is entered by a call to
-the message after the
-Entering break read-eval-print loop ... line is produced
-by the function OnBreakMessage,
+the message at the end starting with you can enter 'quit;' to ...
+is produced by the function OnBreakMessage,
which just like
is a user-configurable global variable
that is a function with no arguments.
OnBreakMessage(); # By default, OnBreakMessage prints the following
-you can 'quit;' to quit to outer loop, or
-you can 'return;' to continue
+you can enter 'quit;' to quit to outer loop, or
+you can enter 'return;' to continue
]]>
Perhaps you are familiar with what's possible in a break loop, and so
@@ -718,7 +700,6 @@ calling as we did above, now produces:
gap> Error("!\n");
Error, !
Hello
-Entering break read-eval-print loop ...
brk> quit; # to get back to outer loop
]]>
@@ -770,7 +751,8 @@ Error, user interrupt
@ GAPROOT/lib/stbc.gi:18
( )
called from read-eval loop at *stdin*:2
-you can 'return;'
+you can enter 'quit;' to quit to outer loop, or
+you can enter 'return;' to continue
brk> Where(2);
*[1] genlabels := Filtered( genlabels, function ( x )
return pnt ^ sgs[x] = pnt;
@@ -843,17 +825,18 @@ gap> test:= function( n )
> if n > 3 then Error( "!\n" ); fi; test( n+1 ); end;;
gap> test( 1 );
Error, !
-you can 'quit;' to quit to outer loop, or
-you can 'return;' to continue
+you can enter 'quit;' to quit to outer loop, or
+you can enter 'return;' to continue
brk> Where();
+Stack trace:
*[1] Error( "!\n" );
- @ *stdin*:4
+ @ *stdin*:3
[2] test( n + 1 );
- @ *stdin*:4
+ @ *stdin*:3
[3] test( n + 1 );
- @ *stdin*:4
+ @ *stdin*:3
[4] test( n + 1 );
- @ *stdin*:4
+ @ *stdin*:3
( )
called from read-eval loop at *errin*:1
brk> n;
@@ -862,28 +845,30 @@ brk> DownEnv();
brk> n;
3
brk> Where();
+Stack trace:
[1] Error( "!\n" );
- @ *stdin*:4
+ @ *stdin*:3
*[2] test( n + 1 );
- @ *stdin*:4
+ @ *stdin*:3
[3] test( n + 1 );
- @ *stdin*:4
+ @ *stdin*:3
[4] test( n + 1 );
- @ *stdin*:4
+ @ *stdin*:3
( )
called from read-eval loop at *errin*:5
brk> DownEnv( 2 );
brk> n;
1
brk> Where();
+Stack trace:
[1] Error( "!\n" );
- @ *stdin*:4
+ @ *stdin*:3
[2] test( n + 1 );
- @ *stdin*:4
+ @ *stdin*:3
[3] test( n + 1 );
- @ *stdin*:4
+ @ *stdin*:3
*[4] test( n + 1 );
- @ *stdin*:4
+ @ *stdin*:3
( )
called from read-eval loop at *errin*:8
brk> DownEnv( -2 );
@@ -923,8 +908,8 @@ Stack trace:
@ *stdin*:7
( )
called from read-eval loop at *stdin*:8
-you can 'quit;' to quit to outer loop, or
-you can 'return;' to continue
+you can enter 'quit;' to quit to outer loop, or
+you can enter 'return;' to continue
brk> x;
1
brk> DownEnv(1);
diff --git a/doc/ref/types.xml b/doc/ref/types.xml
index 32ffe77b0c..b49fe1ad2f 100644
--- a/doc/ref/types.xml
+++ b/doc/ref/types.xml
@@ -601,12 +601,9 @@ for an object.
Setter( prop )( Rationals, false );
-You cannot set an "and-filter" except to true
-not in any function
-Entering break read-eval-print loop ...
-you can 'quit;' to quit to outer loop, or
-you can type 'return true;' to set all components true
-(but you might really want to reset just one component) to continue
+Error, You cannot set an "and-filter" except to true
+not in any function at *stdin*:8
+you can enter 'quit;' to quit to outer loop
brk>
]]>
diff --git a/doc/tut/group.xml b/doc/tut/group.xml
index 3d19ea2713..a47c55dec9 100644
--- a/doc/tut/group.xml
+++ b/doc/tut/group.xml
@@ -928,11 +928,12 @@ gap> Size( Image( hom, DerivedSubgroup(s4) ) );
PreImage( hom, (1,2,3) );
Error,
diff --git a/doc/tut/lists.xml b/doc/tut/lists.xml
index d79908c21e..e2f8393cc6 100644
--- a/doc/tut/lists.xml
+++ b/doc/tut/lists.xml
@@ -341,11 +341,9 @@ gap> list[3][5] := 'w';; list; copy;
[ 1, 2, "threw", [ 4 ] ]
[ 1, 2, "three", [ 4 ] ]
gap> copy[3][5] := 'w';
-List Assignment: must be a mutable list
-not in any function
-Entering break read-eval-print loop ...
-you can 'quit;' to quit to outer loop, or
-you can 'return;' and ignore the assignment to continue
+Error, List Assignment: must be a mutable list
+not in any function at *stdin*:3
+you can enter 'quit;' to quit to outer loop
brk> quit;
]]>
diff --git a/doc/tut/migrat.xml b/doc/tut/migrat.xml
deleted file mode 100644
index bf73228ae0..0000000000
--- a/doc/tut/migrat.xml
+++ /dev/null
@@ -1,1226 +0,0 @@
-
-
-
-
-
-
-
-
-Migrating to &GAP; 4
-
-This chapter is intended to give users who have experience with &GAP; 3
-some information about what has changed in &GAP; 4.
-
-In particular, it informs about changed command line options
-(see ),
-the new global variable fail (see ),
-some functions that have changed their behaviour
-(see ) or their names
-(see ),
-and some conventions used for variable names (see ).
-
-Then the new concepts of &GAP; 4 are sketched,
-first that of mutability or immutability (see ),
-with the explanation of related changes in functions that copy objects
-(see ),
-then the concepts of operations and method selection, which are compared
-with the use of operations records in &GAP; 3
-(see , ,
-and ).
-
-More local changes affect the concepts of notions of generation
-(see ),
-of parents (see ),
-of homomorphisms (see ,
-,
-and ),
-how elements in finitely presented groups are treated
-(see ),
-how information about progress of computations can be obtained
-(see ),
-and how one gets information in a break loop
-(see ).
-
-While a &GAP; 3 compatibility mode is provided
-(see ),
-its use will disable some of the new features of &GAP; 4.
-Also it certainly can only try to provide partial compatibility.
-
-For a detailed explanation of the new features and concepts of &GAP; 4,
-see the manual Programming in GAP.
-
-
-
-
-Changed Command Line Options
-
-In &GAP; 4, the -l option is used to specify the root directory
-(see )
-of the &GAP; distribution,
-which is the directory containing the lib and doc subdirectories.
-Note that in &GAP; 3 this option was used to specify the path to the
-lib directory.
-
-The -h option of &GAP; 3 has been removed,
-the path(s) for the documentation are deduced automatically in &GAP; 4.
-
-The option -g is now used to print information only about full garbage
-collections.
-The new option -g -g generates information about partial
-garbage collections too.
-
-
-
-
-
-
-Fail
-
-There is a new global variable
-fail instead of false
-
-
-
-
-in &GAP; 4.
-It is intended as a return value of a function for the case that it
-could not perform its task.
-For example, Inverse returns fail if it is called with a singular
-matrix, and Position returns fail if the second argument is not
-contained in the list given as first argument.
-
-&GAP; 3 handled such situations by either signalling an error,
-for example if it was asked for the inverse of a singular matrix,
-or by (mis)using false as return value, as in the example Position.
-Note that in the first example, in &GAP; 3 it was necessary to check
-the invertibility of a matrix before one could safely ask for its
-inverse, which meant that roughly the same work was done twice.
-
-
-
-
-
-
-
-
-Changed Functionality
-
-Some functions that were already available in &GAP; 3 behave
-differently in &GAP; 4. This section lists them.
-
-
-
-
-The &GAP; 3 manual promised that pnt would be the first entry of the
-resulting orbit. This was wrong already there in a few cases, therefore
-&GAP; 4 does not promise anything about the ordering of points in an orbit.
-
-
-
-
-
-
-only takes the element g and computes its multiplicative order.
-Calling Order with two arguments is permitted only in the
-&GAP; 3 compatibility mode, see .
-(Note that it does not make sense anymore to specify a group as
-first argument w.r.t. which the order of the second argument shall
-be computed, see .)
-
-
-
-
-
-
-If obj is not contained in the list list then fail is returned
-in &GAP; 4 (see ), whereas false was returned in &GAP; 3.
-
-
-
-
-
-
-In &GAP; 3, this function took either two or three arguments,
-the optional argument K being a subgroup of G that stabilizes prop
-in the sense that for any element g in G,
-either all elements or no element in the coset g * K have the
-property prop.
-
-The &GAP; 4 function ElementProperty, however,
-takes between two and four arguments,
-and the subgroup K known from &GAP; 3 has to be entered as the fourth
-argument not the third.
-(The third argument in the &GAP; 4 function denotes a subgroup U
-stabilizing prop in the sense that either all elements or no element
-in right cosets U * g have the property prop.)
-
-(This discrepancy was discovered only in March 2002,
-short before the release of &GAP; 4.3.)
-
-
-
-
-
-
-Objects may appear on the screen in a different way,
-depending on whether they are printed by the read eval print loop
-or by an explicit call of Print.
-The reason is that the read eval print loop calls the operation ViewObj
-and not PrintObj, whereas Print calls PrintObj for each of its
-arguments.
-This permits the installation of methods for printing objects in a short form
-in the read eval print loop while retaining Print to display
-the object completely.
-See also Section .
-
-(PrintObj is installed as standard method ViewObj, so it is
-not really necessary to have a ViewObj method for an object.)
-
-
-
-
-
-
-In &GAP; 3, PrintTo could be (mis)used to redirect the text
-printed by a function (that is, not only the output of a function)
-to a file by entering the function call as second argument.
-This was used mainly in order to avoid many calls of AppendTo.
-In &GAP; 4, this feature has disappeared.
-One can use streams (see Chapter )
-instead in order to write files efficiently.
-
-
-
-
-
-
-
-
-Changed Variable Names
-
-AgGroup
-ApplyFunc
-Backtrace
-CharTable
-Denominator
-DepthVector
-Elements
-IsBijection
-IsFunc
-IsMat
-IsRec
-IsSet
-LengthWord
-NOfCyc
-Numerator
-RandomInvertableMat
-RecFields
-X
-
-Some functions have changed their name without changing the
-functionality.
-A -- probably incomplete -- list follows
-
-
-
-See Section for a way to make the old names
-available again.
-
-
-
-
-
-
-Naming Conventions
-
-The way functions are named has been unified in &GAP; 4.
-This might help to memorize or even guess names of library functions.
-
-If a variable name consists of several words then the first
-letter of each word is capitalized.
-
-If the first part of the name of a function is a verb then the function
-may modify its argument(s) but does not return anything,
-for example Append appends the list given as second argument to the
-list given as first argument.
-Otherwise the function returns an object without changing the arguments,
-for example Concatenation returns the concatenation of the lists
-given as arguments.
-
-If the name of a function contains the word By then the return value is
-thought of as built in a certain way from the parts given as arguments.
-For example, GroupByGenerators returns a group built from its group
-generators, and creating a group as a factor group of a given group
-by a normal subgroup can be done by taking the image of
-NaturalHomomorphismByNormalSubgroup
-(see also ).
-Other examples of By functions are GroupHomomorphismByImages and
-UnivariateLaurentPolynomialByCoefficients.
-
-If the name of a function contains the word Of then the return value is
-thought of as information deduced from the arguments.
-Usually such functions are attributes
-(see in this Tutorial and ).
-Examples are GeneratorsOfGroup, which returns a list of generators for
-the group entered as argument, or DiagonalOfMat.
-
-For the setter and tester functions of an attribute attr
-(see in this Tutorial
-and )
-the names Setattr resp. Hasattr are available.
-
-If the name of a function fun1 ends with NC then there is another
-function fun2 with the same name except that the NC is missing.
-NC stands for no check.
-When fun2 is called then it checks whether its arguments are valid,
-and if so then it calls fun1.
-The functions SubgroupNC and Subgroup are a typical example.
-
-The idea is that the possibly time consuming check of the arguments
-can be omitted if one is sure that they are unnecessary.
-For example, if an algorithm produces generators of the derived subgroup
-of a group then it is guaranteed that they lie in the original group;
-Subgroup would check this, and SubgroupNC omits the check.
-
-Needless to say, all these rules are not followed slavishly,
-for example there is one operation Zero instead of two operations
-ZeroOfElement and ZeroOfAdditiveGroup.
-
-
-
-
-
-
-Immutable Objects
-
-&GAP; 4 supports immutable objects. Such objects cannot be
-changed, attempting to do so issues an error. Typically attribute
-values are immutable, and also the results of those binary arithmetic
-operations where both arguments are immutable,
-see Section .
-For example, [ 1 .. 100 ] + [ 1 .. 100 ] is a
-mutable list and 2 * Immutable( [ 1 .. 100 ] ) is an immutable
-list, both are equal to the (mutable) list [ 2, 4 .. 200 ].
-
-There is no way to make an immutable object mutable, one can only
-get a mutable copy by ShallowCopy. The other way round,
-MakeImmutable makes a (mutable or immutable) object and all its
-subobjects immutable; one must be very careful to use MakeImmutable
-only for those objects that are really newly created, for such objects
-the advantage over Immutable is that no copy is made.
-
-More about immutability can be found in Sections in
-this tutorial and .
-
-
-
-
-
-
-Copy
-
-StructuralCopy
-ShallowCopy
-The function Copy of &GAP; 3 is not supported in &GAP; 4. This
-function was used to create a copy cop of its argument obj with
-the properties that cop and obj had no subobjects in common and
-that if two subobjects of obj were identical then also the
-corresponding subobjects of cop were identical.
-
-The possibility of having immutable objects (see ) can and
-should be used to avoid unnecessary copying.
-Namely, given an immutable object one needs to copy it only if one wants
-to get a modified object, and in such a situation usually it is
-sufficient to use ShallowCopy, or at least one knows how deep one must
-copy in order to do the changes one has in mind.
-
-For example, suppose you have a matrix group, and you want to
-construct a list of matrices by modifying the group generators. This
-list of generators is immutable, so you call ShallowCopy to get a
-mutable list that contains the same matrices. If you only want to
-exchange some of them, or to append some other matrices, this shallow
-copy is already what you need. So suppose that you are interested in
-a list of matrices where some rows are also changed. For that, you
-call ShallowCopy for the matrices in question, and you get matrices
-whose rows can be changed. If you want to change single entries in
-some rows, ShallowCopy must be called to get mutable copies of these
-rows. Note that in all these situations there is no danger to change,
-i.e., to destroy the original generators of the matrix group.
-
-If one needs the facility of the Copy function of &GAP; 3 to get a
-copy with the same structure then one can use the new &GAP; 4
-function StructuralCopy. It returns a structural copy that has no
-mutable subobject in common with its argument. So if
-StructuralCopy is called with an immutable object then this object
-itself is returned, and if StructuralCopy is called with a mutable
-list of immutable objects then a shallow copy of this list is
-returned.
-
-Note that ShallowCopy now is an operation. So if you create your
-own type of (copyable) objects then you must define what a shallow
-copy of these objects is, and install an appropriate method.
-
-
-
-
-
-
-Attributes vs. Record Components
-
-In &GAP; 3, many complex objects were represented via records, for
-example all domains. Information about these objects was stored in
-components of these records. For the user, this was usually not
-relevant, since there were functions for computing information about
-the objects in question. For example, if one was interested in the
-size of a group then one could call Size.
-
-But since it was guaranteed that the size of a domain D was stored
-as value of the component size, it was allowed to access D.size
-if this component was bound, and a check for this was possible via
-IsBound( D.size ).
-
-In &GAP; 4, only the access via functions is admissible. One reason
-is the following basic rule.
-
-From the information that a given &GAP; 4 object is for example a
-domain, one cannot conclude that this object has a certain
-representation.
-
-For attributes like Size, &GAP; 4 provides two related functions,
-the setter and the tester of the attribute, which can be used to
-set an attribute value and to check whether the value of an attribute
-is already stored for an object (see also ). For example, if D is a domain in &GAP; 4 then
-HasSize( D ) is true if the size of D is already stored, and
-false otherwise. In the latter case, if you know that the size of
-D is size then you may store it by SetSize( D, size ).
-
-Besides the flexibility in the internal representation of objects,
-storing information only via function calls has also the advantage
-that &GAP; 4 is able to draw conclusions automatically. For example,
-as soon as it is stored that a group is nilpotent, it is also stored
-that it is solvable, see Chapters and
-for the details.
-
-As a consequence, you cannot put your favourite information into a
-domain D by assigning it to a new component like
-D.myPrivateInfo. Instead you can introduce a new attribute and
-then use its setter, see .
-
-
-
-
-
-
-Different Notions of Generation
-
-As in &GAP; 3, a domain in &GAP; 4 is a structured set.
-
-The same set can have different structures, for example a field can be
-regarded as a ring or as an algebra or vector space over a subfield.
-
-In &GAP; 3, however, an object representing a ring did not represent
-a field, and an object representing a field did not represent a ring.
-One reason for this was that the record component generators was
-used to denote the appropriate generators of the domain. For a ring
-R, the component R.generators was a list of ring generators, and
-for a field F, F.generators was a list of field generators.
-
-&GAP; 4 cleans this up, see . It supports
-many different notions of generation, for example one can ask for
-magma generators of a group or for generators of a field as an additive
-group. A subtle but important distinction is that between generators
-of an algebra and of an algebra-with-one.
-
-So the attributes GeneratorsOfGroup, GeneratorsOfMagma,
-GeneratorsOfRing, GeneratorsOfField, GeneratorsOfVectorSpace,
-and so on, replace the access to the generators component.
-
-
-
-
-
-
-Operations Records
-
-Already in &GAP; 3 there were several functions that were applicable
-to many different kinds of objects, for example Size could be
-applied to any domain, and the binary infix multiplication * could
-be used to multiply two matrices, an integer with a row vector, or a
-permutation with a permutation group. This was implemented as
-follows. Functions like Size and * tried to find out what
-situation was described by its arguments, and then it called a more
-specific function to compute the desired information. These more
-specific functions, let us call them methods as they are also called
-in &GAP; 4, were stored in so-called operations records of the
-arguments.
-
-For example, every domain in &GAP; 3 was represented as a record, and
-the operations record was stored in the record component operations.
-If Size was called for the domain then the method to compute the
-size of the domain was found as value of the Size component of the
-operations record.
-
-This was fine for functions taking only one argument, and in principle
-it is possible that for those functions an object stored an optimal
-method in its operations record. But in the case of more arguments
-this is not possible. In a multiplication of two objects in &GAP; 3,
-one had to choose between the methods stored in the operations records
-of the arguments, and if for example the method stored for the left
-operand was called, this method had to handle all possible right
-operands.
-
-So operations records turned out to be not flexible enough.
-In &GAP; 4, operations records are not supported
-(see for a possibility
-to use your &GAP; 3 code that utilizes operations records,
-at least to some extent).
-A detailed description
-of the new mechanism to select methods can be found in
-Chapter .
-
-An important point is that the new mechanism allows &GAP; to take the
-relation between arguments into account. So it is possible (and
-recommended) to install different methods for different relations
-between the arguments. Note that such methods need not do the
-extensive argument checking that was necessary in &GAP; 3, because
-most of the checks are done already by the method selection mechanism.
-
-
-
-
-
-
-Operations vs. Dispatcher Functions
-
-&GAP; 3 functions like Size, CommutatorSubgroup, or
-SylowSubgroup did mainly call an appropriate method
-(see )
-after they had checked their arguments.
-Such functions were
-called dispatchers in &GAP; 3. In &GAP; 4, many dispatchers have
-been replaced by operations, due to the fact that methods are no
-longer stored in operations records (see for the details).
-
-Most dispatchers taking only one argument were treated in a special
-way in &GAP; 3, they had the additional task of storing computed
-values and using these values in subsequent calls. For example, the
-dispatcher Size first checked whether the size of the argument was
-already stored, and if so then this value was returned; otherwise a
-method was called, the value returned by this method was stored in the
-argument, and then returned by Size.
-
-In &GAP; 4, computed values of operations that take one argument
-(these operations are called attributes) are also stored, only the
-mechanism to achieve this has changed, see
-and .
-
-So the behaviour of Size is the same in &GAP; 3 and &GAP; 4. But
-note that in &GAP; 4, it is not possible to access D.size,
-see .
-As described in ,
-&GAP; 4 does not admit bypassing the dispatcher by
-calling for example D.operations.Size. This was done in &GAP; 3
-often for efficiency reasons, but the method selection mechanism of
-&GAP; 4 is fast enough to make this unnecessary.
-
-If you had written your own dispatchers and put your own methods into
-existing operations records then this code will not work in &GAP; 4.
-See
-and
-for a description of how to define operations
-and to install methods.
-
-Finally, some functions in &GAP; 3 were hidden in
-operations records, e.g., PermGroupOps.MovedPoints.
-These functions became proper operations in &GAP; 4.
-
-
-
-
-
-
-Parents and Subgroups
-
-In &GAP; 3 there was a strict distinction between parent groups and
-subgroups.
-The use of the name parent (instead of supergroup)
-was chosen to indicate that the parent of an object was more than just
-useful information.
-In fact the main reason for the introduction of parents was to provide
-a common roof for example for all groups of polycyclic words that
-belonged to the same PC-presentation, or for all subgroups of a finitely
-presented group (see ).
-A subgroup was never a parent group, and it was possible to create
-subgroups only of parent groups.
-
-In &GAP; 4 this common roof is provided already by the concept of
-families, see .
-Thus it is no longer compulsory to use parent groups at all.
-On the other hand, parents may be used in &GAP; 4 to provide
-information about an object, for example the normalizer of a group in its
-parent group may be stored as an attribute value.
-Note that there is no restriction on the supergroup that is set to be
-the parent,
-it is possible to create a subgroup of
-any group, this group then being the parent of the new subgroup.
-This permits for example chains of subgroups with respective parents,
-of arbitrary length.
-
-As a consequence, the Parent command cannot be used in &GAP; 4 to
-test whether the two arguments of CommutatorSubgroup fit together,
-this is now a question that concerns the relation between the families
-of the groups. So the 2-argument version of Parent and the now
-meaningless function IsParent have been abolished.
-
-
-
-
-
-
-Homomorphisms vs. General Mappings
-
-In &GAP; 3 there had been a confusion between group homomorphisms and
-general mappings, as GroupHomomorphismByImages created only a
-general mapping that did not store whether it was a mapping. This
-caused expensive, unwanted, and unnecessary tests whether the mapping
-was in fact a group homomorphism. Moreover, the official
-workaround to set some components of the mapping record was quite
-unwieldy.
-
-In &GAP; 4, GroupHomomorphismByImages checks whether the desired
-mapping is indeed a group homomorphism; if so then this property is
-stored in the returned mapping, otherwise fail is returned. If you
-want to avoid the checks then you can use
-GroupHomomorphismByImagesNC. If you want to check whether a general
-mapping that respects the group operations is really a group
-homomorphism, you can construct it via GroupGeneralMappingByImages
-and then call IsGroupHomomorphism for it. (Note that
-IsGroupHomomorphism returns true if and only if both
-IsGroupGeneralMapping and IsMapping do, so one does in fact check
-IsMapping in this case.)
-
-There is no function IsHomomorphism in &GAP; 4,
-since there are several different operations with respect to which a
-mapping can be a homomorphism.
-
-
-
-
-
-
-Homomorphisms vs. Factor Structures
-
-If F is a factor structure of G, with kernel N, complete
-information about the connection between F and G is provided by
-the natural homomorphism.
-
-In &GAP; 3, the official way to construct this natural homomorphism
-was to create first the factor structure F, and then to call
-NaturalHomomorphism with the arguments G and F.
-For that, the data necessary to compute the homomorphism was stored in
-F when F was constructed.
-
-In &GAP; 4, factor structures are not treated in a special way,
-in particular they do not store information about a homomorphism.
-Instead, the more natural way is taken to construct the natural
-homomorphism from G and N by NaturalHomomorphismByNormalSubgroup
-if N is a normal subgroup of the group G,
-or by NaturalHomomorphismByIdeal if N is an ideal in the ring G.
-The factor F can then be accessed as the image of this homomorphism,
-and of course G is the preimage and N is the kernel.
-
-Note that &GAP; 4 does not guarantee anything about the representation
-of the factor F, it may be a permutation group or a polycyclically
-presented group or another kind of group.
-Also note that a natural homomorphism need not be surjective.
-
-A consequence of this change is that &GAP; 4 does not allow you to
-construct a natural homomorphism from the groups G and F.
-
-The other common type of homomorphism in &GAP; 3, operation
-homomorphisms, have been replaced (just a name change) by action
-homomorphisms, which are handled in a similar fashion. That is, an
-action homomorphism is constructed from an acting group, an action
-domain, and a function describing the operation. The permutation
-group arising by the induced action is then the image of this
-operation homomorphism.
-
-The &GAP; 3 function Operation is still supported, under the name Action,
-but from the original group and the result of Action it is not
-possible to construct the action homomorphism.
-
-
-
-
-
-
-Isomorphisms vs. Isomorphic Structures
-
-In &GAP; 3, a different representation of a group could be obtained by
-calling AgGroup to get an isomorphic polycyclically presented group,
-PermGroup to get an isomorphic permutation group, and so on.
-The returned objects stored an isomorphism in the record component
-bijection.
-
-For the same reason as in ,
-&GAP; 4 puts emphasis on the isomorphism,
-and the isomorphic object in the desired representation can be accessed
-as its image.
-So you can call IsomorphismPcGroup or IsomorphismPermGroup in order
-to get an isomorphism to a polycyclically presented group or a
-permutation group, respectively, and then call Image to get the
-isomorphic group.
-
-Note that the image of an action homomorphism with trivial kernel is
-also an isomorphic permutation group, but an action homomorphism need
-not be surjective, since it may be easier to define it into the full
-symmetric group.
-
-Further note that in &GAP; 3, a usual application of isomorphisms to
-polycyclically presented groups was to utilize the usually more
-effective algorithms for solvable groups. However, the new concept of
-polycyclic generating systems in &GAP; 4 makes it possible to apply
-these algorithms to arbitrary solvable groups, independent of the
-representation. For example, &GAP; 4 can handle polycyclic
-generating systems of solvable permutation groups. So in many cases,
-a change of the representation for efficiency reasons may be not
-necessary any longer.
-
-In general IsomorphismFpGroup will define a presentation on generators
-chosen by the algorithm. The corresponding elements of the original
-group can be obtained by the command
-
-PreImagesRepresentative(isofp,i));
-]]>
-
-If a presentation in the given generators is needed, the command
-IsomorphismFpGroupByGenerators(G, gens) will produce one.
-
-
-
-
-
-
-Elements of Finitely Presented Groups
-
-Strictly speaking, &GAP; 3 did not support elements of finitely
-presented groups. Instead, the words in abstract generators of
-the underlying free groups were (mis)used. This caused problems
-whenever calculations with elements were involved, the most obvious
-ones being wrong results of element comparisons. Also functions
-that should in principle work for any group were not applicable to
-finitely presented groups. In effect, a finitely presented group had
-to be treated in a special way in &GAP; 3.
-
-&GAP; 4 distinguishes free groups and their elements from finitely
-presented groups and their elements. Comparing two elements of a
-finitely presented group will yield either the correct result or no
-result at all.
-
-Note that in &GAP; 4, the arithmetic and comparison operations for
-group elements do not depend on a context provided by a group that
-contains the elements. In particular, in &GAP; 4 it is not
-meaningful to call Order( G, g ) for a group G and an element
-g.
-
-
-
-
-
-
-Polynomials
-
-In &GAP; 3, polynomials were defined over a field. So a polynomial over
-GF(3) was different from a polynomial over GF(9), even if the
-coefficients were exactly the same.
-
-&GAP; 4 defines polynomials only over a characteristic. This makes it
-possible for example to multiply a polynomial over GF(3) with a polynomial
-over GF(9) without the need to convert the former to the larger field.
-
-However it has an effect on the result of DefaultRing for polynomials:
-In &GAP; 3 the default ring for a polynomial was the polynomial ring of the
-field over which the polynomial was defined. In &GAP; 4 no field is
-associated, so (to avoid having to define the algebraic closure as the only
-other sensible alternative) the default ring of a polynomial is the
-DefaultRing of its coefficients.
-
-This has an effect on Factors: If no ring is given, a polynomial is
-factorized over its DefaultRing and so Factors(poly)
-might return different results.
-
-To be safe from this problem, if you are not working over prime fields,
-rather call Factors(pring,poly) with the appropriate polynomial ring
-and change your code accordingly.
-
-
-
-
-
-
-The Info Mechanism
-
-Sometimes it is useful to get information about the progress of a
-calculation.
-Many &GAP; functions contain statements to display such information
-under certain conditions.
-
-In &GAP; 3, these statements were calls to functions such as
-InfoGroup1 or InfoGroup2, and if the user assigned Print to
-these variables then this had the effect to switch on the printing of
-information.
-InfoGroup2 was used for more detailed information than InfoGroup1.
-One could switch off the printing again by assigning Ignore to the
-variables, and Ignore was also the default value.
-
-&GAP; 4 uses one function Info for the same purpose,
-which is a function that takes as first argument an info class such as
-InfoGroup, as second argument an info level, and the print statements
-as remaining arguments.
-The level of an info class class is set to level by calling
-SetInfoLevel( class, level ).
-An Info statement is printed only if its second argument is smaller than
-or equal to the current info level.
-
- test:= function( obj )
-> Info( InfoGroup, 2, "This is useful, isn't it?" );
-> return obj;
-> end;;
-gap> test( 1 );
-1
-gap> SetInfoLevel( InfoGroup, 2 );
-gap> test( 1 );
-#I This is useful, isn't it?
-1
-]]>
-
-As in &GAP; 3, if an info statement is ignored then its arguments are
-not evaluated.
-
-
-
-
-
-
-Debugging
-
-Backtrace
-DownEnv
-Where
-If &GAP; 4 runs into an error or is interrupted,
-it enters a break loop.
-The command Where( number ), which replaces Backtrace of &GAP; 3,
-can be used to display number lines of information about the current
-function call stack.
-
-As in &GAP; 3, access is only possible to the variables of the current
-level in the function stack,
-but in &GAP; 4 the function DownEnv, with a positive or negative
-integer as argument, permits one to step down or up in the
-stack.
-
-When interrupting, the first line printed by Where actually may be
-one level higher, as shown below.
-
- OnBreak := function() Where(0); end;; # eliminate back-tracing on
-gap> # entry to break loop
-gap> test:= function( n )
-> if n > 3 then Error( "!\n" ); fi; test( n+1 ); end;;
-gap> test( 1 );
-Error, !
-at *stdin*:6
-you can 'quit;' to quit to outer loop, or
-you can 'return;' to continue
-brk> Where();
-*[1] Error( "!\n" );
- @ *stdin*:4
- [2] test( n + 1 );
- @ *stdin*:4
- [3] test( n + 1 );
- @ *stdin*:4
- [4] test( n + 1 );
- @ *stdin*:4
-( )
- called from read-eval loop at *errin*:1
-brk> n;
-4
-brk> DownEnv();
-brk> n;
-3
-brk> Where();
- [1] Error( "!\n" );
- @ *stdin*:4
-*[2] test( n + 1 );
- @ *stdin*:4
- [3] test( n + 1 );
- @ *stdin*:4
- [4] test( n + 1 );
- @ *stdin*:4
-( )
- called from read-eval loop at *errin*:5
-brk> DownEnv( 2 );
-brk> n;
-1
-brk> Where();
- [1] Error( "!\n" );
- @ *stdin*:4
- [2] test( n + 1 );
- @ *stdin*:4
- [3] test( n + 1 );
- @ *stdin*:4
-*[4] test( n + 1 );
- @ *stdin*:4
-( )
- called from read-eval loop at *errin*:8
-brk> DownEnv( -2 );
-brk> n;
-3
-brk> quit;
-gap> OnBreak := Where;; # restore OnBreak to its default value
-]]>
-
-For purposes of debugging, it can be helpful sometimes, to see what
-information is stored within an object. In &GAP; 3 this was possible using
-RecFields because the objects in question were represented via records.
-For component objects, &GAP; 4 permits the same by
-NamesOfComponents( object ), which will list all components present.
-
-
-
-
-
-
-Compatibility Mode
-
-For users who want to use &GAP; 3 code with as little changes as
-possible, a compatibility mode is provided by &GAP; 4.
-This mode must be turned on explicitly by the user.
-
-It should be noted that this compatibility mode has not been tested
-thoroughly.
-
-The compatibility mode can be turned on by loading some of the following
-files with ReadLib.
-The different files address different aspects of compatibility.
-
-
-compat3a.g
-
- makes some &GAP; 3 function names available that were changed
- in &GAP; 4,
- and provides code for some &GAP; 3 features that were
- deliberately left out from the &GAP; 4 library.
- For example,
- almost all variable names concerning character theory that are
- mentioned in the &GAP; 3 manual,
- such as CharTable and SubgroupFusions,
- are available after compat3a.g has been read;
- the only exceptions are names of operations records.
-
-compat3b.g
-
- implements the availability of components of domains;
- besides components that have no meaning for the rest of the &GAP; 4
- library, such as D.myInfo, there are components associated to
- attributes; for example D.size is redirected to the call of the
- attribute Size, IsBound( D.size ) to the call of its tester,
- and D.size:= val to the call of its setter.
- (An important special case is the component operations, see below.)
-
-compat3c.g
-
- permits you to implement your own elements represented as records,
- and using operations records to provide a Print method and
- the basic arithmetic operations.
- When using operations records, it is probably a good idea to
- use immutable operations records; for example, if the results
- of arithmetic operations are records with operations records then
- this avoids to create shallow copies of the operations records
- in the call to Immutable for the results.
-
-
-
-The following features are accessible only via starting &GAP; with
-the command line option -O and may damage some features of &GAP; 4
-permanently for the current session.
-
- With this option, also the files listed above are read automatically.
-
-
-compat3d.g
-
- provides some &GAP; 3 functions like Domain, simulates the
- &GAP; 3 behaviour of IsString (to convert a list to string
- representation if possible), and replaces fail by false;
- these changes destroy parts of the functionality of &GAP; 4.
-
-
-
-Some words concerning the simulation of operations records may be
-necessary.
-
-The operations records of the &GAP; 3 library, such as DomainOps
-and GroupOps, are available only for access to their components,
-whose values are &GAP; 4 operations; for example, the value of both
-DomainOps.Size and GroupOps.Size is the operation Size. So it
-is not safely possible to delegate from a Size method in another
-operations record to DomainOps.Size. Also it is not possible to
-change these predefined operations records.
-
-If one wants to install individual methods for a given object obj
-via the mechanism of operations records then one can construct a new
-operations record with OperationsRecord, assign the desired methods
-to components of this record, and then assign the operations record to
-obj.operations. Whenever an operation that is associated with a
-component nam of the operations record is called with obj as first
-argument, the value of nam is chosen as the method.
-
-In the case of the binary operations =, <, +, -, *, /,
-Comm, and LeftQuotient,
-this also happens if obj is the right-hand argument.
-As in &GAP; 3, if both arguments of one of the above binary operations
-have operations records containing a function for this operation,
-then the function in the operations record of the right-hand argument
-is chosen.
-
-We give a small example how the compatibility mode works.
-
-Suppose we want to deal with new objects that are derived from known
-field elements by distorting their multiplication. Namely, let a'
-and b' be the new objects corresponding to the field elements a,
-b, and define a' * b' = a b - a - b + 2.
-
-In &GAP; 3, this problem was solved by representing each new object
-by a record that stored the corresponding old object and an
-operations record, where the latter was a record containing the
-functions applicable to the new object. After the library file
-compat3c.g has been read, we can use this construction of the
-operations record and of the new objects. Note that operations
-records must be created with the function OperationsRecord (this was
-also the norm in &GAP; 3), starting with an empty record would not work.
-For our intended application, we thus start with the following two
-lines of code.
-
- ReadLib( "compat3c.g" );
-gap> MyOps:= OperationsRecord( "MyOps" );;
-HasMyOps := NewFilter( "HasMyOps" );
-]]>
-
-In order to make the translation from &GAP; 3 code to &GAP; 4
-easier, &GAP; prints the definition of filters associated with
-operations records and the method installations for operations
-corresponding to components of the operations records. The output
-line printed by &GAP; after the call of OperationsRecord is one
-such case.
-
-Now we add our multiplication function to the operations record,
-and again &GAP; 4 prints a translation to &GAP; 4 code.
-
- MyOps.\* := function( a, b )
-> return rec( x:= a.x * b.x - a.x - b.x + 2,
-> operations := MyOps );
-> end;;
-# If the following method installation matches the requirements
-# of the operation `PROD' then `InstallMethod' should be used.
-# It might be useful to replace the rank `SUM_FLAGS' by `0'.
-InstallOtherMethod( PROD,
- "for object with `MyOps' as first argument",
- true,
- [ HasMyOps, IsObject ], SUM_FLAGS,
- MyOps.\* );
-
-# For binary infix operators, a second method is installed
-# for the case that the object with `MyOps' is the right operand;
-# since this case has higher priority in GAP 3, the method is
-# installed with higher rank `SUM_FLAGS + 1'.
-InstallOtherMethod( PROD,
- "for object with `MyOps' as second argument",
- true,
- [ IsObject, HasMyOps ], SUM_FLAGS + 1,
- MyOps.\* );
-]]>
-
-Let us look how this installation works.
-
- a:= rec( x:= 3, operations:= MyOps );
-rec( x := 3, operations := MyOps )
-gap> b:= rec( x:= 5, operations:= MyOps );
-rec( x := 5, operations := MyOps )
-gap> a * b;
-rec( x := 9, operations := MyOps )
-]]>
-
-(In more complicated cases, we might run into problems, but this was
-already the case in &GAP; 3. For example, suppose we want to support
-the multiplication of two operands having different operations
-records; then it is not clear which of the two multiplication
-functions is to be chosen, and in &GAP; 3, the only way out was to
-change the multiplication functions, in order to make them aware of
-such situations.)
-
-If we are now interested to translate the code to &GAP; 4 in the
-sense that no compatibility mode is needed, we can use what &GAP; 4
-has printed above. (The same example is dealt with in
-Chapter .)
-
-The objects will no longer be records with operations component.
-Instead of records we may use so-called component objects
-with record-like access to components,
-and instead of the operations component, we give the objects a
-type that has the filter HasMyOps set.
-
-
-
-(More about families and representations in this context can be found
-in the chapter of Programming in &GAP; mentioned above.)
-
-The next step is to write a function that creates a new object.
-It may look as follows.
-
-
-
-The multiplication function shall return an object with the
-filter HasMyOp, so we change it as follows.
-
- MyMult := function( a, b )
-> return MyObject( x:= a!.x * b!.x - a!.x - b!.x + 2 );
-> end;;
-]]>
-
-Note that the component access for these objects
-works via !. instead of .;
-further note that no operations record needs to appear here,
-the filter takes its role.
-
-Finally, we install the multiplication for at least one argument
-with the new filter, as had been printed by &GAP; 4 in the
-session shown above.
-
-
-
-And now it works (again).
-
- a:= MyObject( 3 );
-
-gap> b:= MyObject( 5 );
-
-gap> a * b;
-
-gap> last!.x
-9
-]]>
-
-We may install a method to print our objects in a nice way;
-we could have done this for the operations record MyOps
-in the compatibility mode,
-the printed output would look similar to the following.
-
-
-
-Now output looks as follows.
-
- a; b; a * b;
-MyObject( 3 )
-MyObject( 5 )
-MyObject( 9 )
-]]>
-
-Maybe now we want to improve the installation.
-The multiplication function we want to use is apparently
-thought only for the case that both operands have
-the filter HasMyOps (and a component x).
-So it is reasonable to replace the two methods for
-the multiplication by one method for which both arguments
-are required to have the filter.
-
-
-
-At first sight, the &GAP; 4 approach seems to be much more
-complicated.
-But the last example shows that in &GAP; 4,
-each method can be installed more specifically for the appropriate
-situation.
-Moreover, it is for example possible to install a method
-for the multiplication of an integer and a HasMyOps object;
-note that --contrary to the situation in &GAP; 3--
-such a method is independent from already existing methods
-in the sense that these need not be changed when
-new functionality is added.
-
-Another example that uses this part of the compatibility mode can be
-found in the file tst/compat3.tst of the &GAP; 4 distribution.
-
-
-
-
-
-
-
-
diff --git a/doc/tut/opers.xml b/doc/tut/opers.xml
index 6413348e73..313bdc7faf 100644
--- a/doc/tut/opers.xml
+++ b/doc/tut/opers.xml
@@ -218,7 +218,7 @@ stops with an error message of the form
Error, no method found! For debugging hints type ?Recovery from NoMethodFound
Error, no 1st choice method found for `Size' on 1 arguments
called from read-eval loop at *stdin*:2
-type 'quit;' to quit to outer loop
+you can enter 'quit;' to quit to outer loop
]]>
You would get an error message as above if you asked for Size( 1 ).
diff --git a/doc/versiondata b/doc/versiondata
index 98c2758afa..a2eec48b00 100644
--- a/doc/versiondata
+++ b/doc/versiondata
@@ -4,7 +4,7 @@ Instead edit either the template file `doc/versiondata.in`, or edit
`Makefile.rules` (which has code for generating this file), or edit
`configure.ac` (where the value being substituted come from)
-->
-
+
-
+
diff --git a/etc/emscripten/Dockerfile b/etc/emscripten/Dockerfile
new file mode 100644
index 0000000000..9025dbaaa3
--- /dev/null
+++ b/etc/emscripten/Dockerfile
@@ -0,0 +1,50 @@
+# Build environment for compiling GAP to WebAssembly via Emscripten.
+#
+# Pinned to emsdk 3.1.23 for reproducibility. Both pieces of the in-browser
+# REPL are sensitive to the exact toolchain version:
+#
+# - GASMAN, GAP's conservative garbage collector, scans the stack including
+# pointers held in wasm registers, reached via emscripten_scan_registers()
+# (see src/gasman.c). That path is now compiled correctly regardless of
+# version, so the GC itself is no longer the constraint.
+#
+# - The terminal uses xterm-pty, whose emscriptenHack() monkey-patches
+# emscripten's internal TTY device so GAP's tcsetattr() (turning off echo
+# and canonical mode) reaches the line discipline. That patch is tied to
+# emscripten's TTY internals: on 3.1.47 the ioctl no longer reaches
+# xterm-pty, echo stays on, and every typed line is echoed twice.
+#
+# 3.1.23 is the version where the pinned xterm-pty (0.9.4) works. Bump both
+# together and re-test the REPL -- including that typed input is not
+# double-echoed -- before changing this.
+
+FROM emscripten/emsdk:3.1.23
+
+RUN apt-get update && apt-get install -y --no-install-recommends \
+ autoconf \
+ automake \
+ libtool \
+ make \
+ python3 \
+ ca-certificates \
+ curl \
+ bison \
+ byacc \
+ m4 \
+ && rm -rf /var/lib/apt/lists/*
+
+# Allow running as a non-root host UID without breaking the emscripten cache.
+RUN mkdir -p /emsdk/upstream/emscripten/cache \
+ && chmod -R 0777 /emsdk/upstream/emscripten/cache
+
+# Cache the GAP package distribution tarball so container runs don't
+# re-download it from GitHub each time. The URL pins to the "latest"
+# release on the PackageDistro side, so this snapshot drifts as upstream
+# tags new releases — rebuild the image (--no-cache) to refresh.
+ARG GAP_PACKAGES_URL=https://github.com/gap-system/PackageDistro/releases/download/latest/packages.tar.gz
+RUN curl --fail --location --silent --show-error \
+ --output /opt/gap-packages.tar.gz \
+ "$GAP_PACKAGES_URL" \
+ && chmod 0644 /opt/gap-packages.tar.gz
+
+WORKDIR /gap
diff --git a/etc/emscripten/README.md b/etc/emscripten/README.md
index 5946302efe..083de668b6 100644
--- a/etc/emscripten/README.md
+++ b/etc/emscripten/README.md
@@ -1,26 +1,127 @@
-Code to allow building gap to WASM using Emscripten.
+# GAP in the browser
-Files:
+Build GAP as a WebAssembly module and serve it as a self-contained website.
+The terminal interface uses [xterm-pty](https://github.com/mame/xterm-pty),
+so the resulting page behaves like a normal GAP REPL.
-- `build.sh`: Run as `etc/emscripten/build.sh` from a fresh copy of GAP.
+## Quick start
-- `web-template`: Uses 'xterm-pty' to create a "nice" interface to the Wasm GAP.
+From a fresh GAP checkout, with either Docker or Podman installed:
-- `build_startup_manifest.js`: Run it in the web root directory to build `startup_manifest.json` that contains resources to preload.
+```sh
+etc/emscripten/build-in-docker.sh
+cd web-example
+../etc/emscripten/serve.py
+```
+
+Then open . The first build takes 10–30 minutes; the
+docker image, the GAP package distribution, and the GMP/zlib builds are all
+cached for subsequent runs.
+
+To pick up newer GAP packages from upstream, force a fresh image build:
+
+```sh
+docker build --no-cache -t gap-emscripten-build:3.1.23 etc/emscripten/
+```
+
+On Apple Silicon (and other non-amd64 hosts), the build runs `linux/amd64`
+under emulation, since `emscripten/emsdk:3.1.23` is amd64-only on Docker
+Hub. `build-in-docker.sh` pins the platform explicitly so the layer cache
+holds across runs; set `BUILD_PLATFORM` to override.
+
+The output directory `web-example/` is fully self-contained — copy it to any
+static host (see "Hosting" below for the headers it needs).
+
+## Building without Docker
+
+If you already have emsdk 3.1.23 sourced in your shell, you can run the
+underlying build directly:
+
+```sh
+etc/emscripten/build.sh
+etc/emscripten/assemble-website.sh
+```
+
+emsdk 3.1.23 is the version we test against, paired with xterm-pty 0.9.4.
+GAP relies on ASYNCIFY together with GASMAN's conservative GC, which scans
+wasm registers via `emscripten_scan_registers()` (see `src/gasman.c`); and
+the terminal relies on xterm-pty's `emscriptenHack()` patching emscripten's
+TTY device so `tcsetattr()` reaches the line discipline. Both are sensitive
+to the toolchain version (a newer emsdk leaves `tcsetattr` unhonoured, so
+typed input is echoed twice), so re-test the REPL when changing emsdk.
-See 'run-web-demo.sh' as an example on how to set up a working website.
+## Hosting
-Note that this demo uses xterm-pty, a library which provides a terminal interface
-for emscripten-compiled programs. This uses a javascript feature called
-"SharedArrayBuffer", which requires some headers are returned by the server:
+The xterm-pty terminal uses `SharedArrayBuffer`, which browsers only allow
+when the page is served with these two headers:
```
Cross-Origin-Opener-Policy: same-origin
Cross-Origin-Embedder-Policy: require-corp
```
-For more details, see for [this article](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/SharedArrayBuffer).
+`serve.py` is a 20-line stdlib-only Python server that adds them. For
+GitHub Pages and other static hosts that don't let you set headers,
+`web-template/coi-serviceworker.js` is included as a workaround (it
+re-fetches resources through a service worker that adds the headers).
+
+## Files
+
+| File | Role |
+| ---- | ---- |
+| `build-in-docker.sh` | One-stop entry point. Builds the image, runs `build.sh` inside, then `assemble-website.sh`. |
+| `Dockerfile` | Pinned `emscripten/emsdk:3.1.23` with autotools, python3, bison/byacc/m4, and a baked-in copy of the GAP package distribution tarball at `/opt/gap-packages.tar.gz`. |
+| `build.sh` | Configures and builds GMP, zlib, and GAP itself for wasm. |
+| `assemble-website.sh` | Copies the build outputs and data directories (`pkg`, `lib`, `grp`, …) into `web-example/`. |
+| `generate_gap_fs_json.py` | Reads file paths on stdin, writes `gap-fs.json` (the manifest of every file in the virtual FS). |
+| `startup_manifest.json` | List of files to fetch eagerly at startup, captured from a real GAP run. Anything not in this list is fetched lazily on first read. See "Updating the startup manifest" below for how to refresh it. |
+| `serve.py` | Local server that adds the COOP/COEP headers. |
+| `web-template/` | Static UI: `index.html`, the worker scripts, the FS init shim, and the COOP/COEP service worker for hosts where you can't set headers. |
+
+## Updating the startup manifest
+
+`startup_manifest.json` lists files (relative to the GAP root) that the FS
+init shim downloads up front instead of lazily. The current list was
+captured from a real GAP run reaching its prompt, so it includes both
+the core library bootstrap (`lib/init.g`, `lib/read*.g`, …) and any
+default-loaded packages. Entries that no longer exist in the build are
+silently ignored, so it is safe to leave stale entries in place; it is
+also safe to leave the list empty (every file becomes lazy).
+
+The manifest is a startup-time optimisation, not a correctness mechanism:
+a wrong list never breaks the build, it only makes startup slower (files
+GAP needs but the manifest omits get fetched lazily, one round-trip each)
+or wastes bandwidth (files in the manifest that GAP doesn't actually
+read are downloaded anyway). So it's worth refreshing when something
+changes the set of files read at startup — most importantly when the
+default loaded packages change, but also after large library reshuffles.
+
+To regenerate it after such changes:
+
+1. Build the website (`build-in-docker.sh`) and serve it (`serve.py`).
+2. **Empty the served manifest before capturing.** Replace
+ `web-example/startup_manifest.json` with `[]` (or delete it).
+ Otherwise the existing entries are eagerly pre-fetched at startup,
+ appear in `fetchedUrls`, and you'll just round-trip the old list.
+ Editing the served file is enough — no rebuild is needed.
+3. Open the page and wait for the GAP prompt to appear. Every file that
+ GAP actually reads now goes through the lazy `XHR` path and gets
+ captured.
+4. Open devtools and read the captured URLs from the page's JS console:
+ `window.fetchedUrls` is an array of every unique URL the worker
+ requested. Chrome/Firefox provide a `copy()` console helper:
+ `copy(JSON.stringify(fetchedUrls))` puts the JSON on your clipboard.
+5. Strip non-GAP-FS entries (`gap.js`, `gap.wasm`, `gap-fs.json`, the
+ xterm CDN URLs) and write the result to
+ `etc/emscripten/startup_manifest.json` (so it's checked in and gets
+ picked up by the next `assemble-website.sh`). A `jq` filter that
+ keeps just GAP filesystem paths:
+
+ ```sh
+ jq '[.[] | select(test("^(pkg|lib|grp|tst|doc|hpcgap|dev|benchmark)/"))]' \
+ fetched-urls.json > etc/emscripten/startup_manifest.json
+ ```
-The file "coi-serviceworker.js" works around this problem on Github pages. This won't
-work locally, so "server.rb" is a simple ruby script, which just starts a web-server
-which returns the required headers.
\ No newline at end of file
+The bookkeeping lives in `web-template/gap-fs.js` (wraps `fetch` and
+`XMLHttpRequest.open` to report URLs to the main thread) and
+`web-template/index.html` (accumulates them onto `window.fetchedUrls`).
diff --git a/etc/emscripten/assemble-website.sh b/etc/emscripten/assemble-website.sh
new file mode 100755
index 0000000000..12e6f6a83b
--- /dev/null
+++ b/etc/emscripten/assemble-website.sh
@@ -0,0 +1,64 @@
+#!/usr/bin/env bash
+#
+# Assemble a self-contained website from a completed wasm build.
+# Outputs ./web-example/ relative to the GAP source root.
+#
+# Run after etc/emscripten/build.sh (or have build-in-docker.sh call it).
+
+set -euo pipefail
+
+SCRIPT_DIR=$(cd "$(dirname "$0")" && pwd)
+ROOT_DIR=$(cd "$SCRIPT_DIR/../.." && pwd)
+OUT_DIR="$ROOT_DIR/web-example"
+
+cd "$ROOT_DIR"
+
+for f in gap.js gap.wasm gap-fs.json; do
+ if [[ ! -f $f ]]; then
+ echo "Error: missing build output '$f'. Run etc/emscripten/build.sh first." >&2
+ exit 1
+ fi
+done
+
+# Always start from a clean output directory. Merging into a previous
+# web-example/ confuses cp when a tree has changed shape between runs
+# (e.g. pkg/X switching between a symlink and a real directory).
+rm -rf "$OUT_DIR"
+mkdir -p "$OUT_DIR"
+
+cp "$SCRIPT_DIR"/web-template/* "$OUT_DIR"/
+cp "$SCRIPT_DIR"/startup_manifest.json "$OUT_DIR"/
+cp gap.js gap.wasm gap-fs.json "$OUT_DIR"/
+# Emscripten only emits a separate gap.worker.js for pthread builds; this
+# single-threaded ASYNCIFY build doesn't use one (newer emscripten inlines
+# the worker regardless). Copy it only if it was produced.
+if [[ -f gap.worker.js ]]; then
+ cp gap.worker.js "$OUT_DIR"/
+fi
+cp LICENSE COPYRIGHT "$OUT_DIR"/
+
+# Data directories. These are referenced by gap-fs.json and either eagerly
+# loaded (if listed in startup_manifest.json) or lazily fetched on first
+# read by Emscripten's createLazyFile.
+#
+# -L dereferences symlinks so the output tree is self-contained (a setup
+# where pkg/X is a symlink into a separate checkout still works). Some
+# packages ship dangling symlinks as build artefacts (e.g. pkg/vole's
+# rust/target/*.dSYM); cp prints those and exits non-zero but still copies
+# everything else, so we don't let that abort the run. The assertion below
+# catches a genuinely incomplete copy.
+for d in pkg lib grp tst doc hpcgap dev benchmark; do
+ cp -RL "$d" "$OUT_DIR"/ 2>/dev/null || true
+done
+
+# pkg/log holds package test logs (.log/.err/.out) that are never read at
+# runtime; keep them out of the shipped site.
+rm -rf "$OUT_DIR/pkg/log"
+
+# The library bootstrap must be present, or GAP 404s during startup.
+if [[ ! -f "$OUT_DIR/lib/init.g" ]]; then
+ echo "Error: lib/init.g missing from $OUT_DIR after copy." >&2
+ exit 1
+fi
+
+echo "Assembled website at $OUT_DIR"
diff --git a/etc/emscripten/build-in-docker.sh b/etc/emscripten/build-in-docker.sh
new file mode 100755
index 0000000000..ac7a7aa604
--- /dev/null
+++ b/etc/emscripten/build-in-docker.sh
@@ -0,0 +1,80 @@
+#!/usr/bin/env bash
+#
+# One-stop shop: build GAP for the web inside a pinned container.
+#
+# Usage (run from the GAP source tree):
+# etc/emscripten/build-in-docker.sh
+#
+# Output: ./web-example/ with a self-contained website. Copy it anywhere
+# and serve with COOP/COEP headers (etc/emscripten/serve.py is one option).
+
+set -euo pipefail
+
+SCRIPT_DIR=$(cd "$(dirname "$0")" && pwd)
+ROOT_DIR=$(cd "$SCRIPT_DIR/../.." && pwd)
+
+RUNTIME="${CONTAINER_RUNTIME:-}"
+if [[ -z "$RUNTIME" ]]; then
+ if command -v podman >/dev/null 2>&1; then
+ RUNTIME=podman
+ elif command -v docker >/dev/null 2>&1; then
+ RUNTIME=docker
+ else
+ echo "Error: neither podman nor docker found in PATH." >&2
+ echo "Install one, or set CONTAINER_RUNTIME explicitly." >&2
+ exit 1
+ fi
+fi
+
+IMAGE_TAG="gap-emscripten-build:3.1.23"
+
+# Pin the platform. emscripten/emsdk:3.1.23 is amd64-only on Docker Hub, so on
+# Apple Silicon (or any non-amd64 host) the runtime would otherwise renegotiate
+# the platform on every build -- that mismatch invalidates the FROM layer's
+# cache and cascades through the whole image, defeating the layer cache even
+# with --layers. Override with BUILD_PLATFORM if needed.
+PLATFORM="${BUILD_PLATFORM:-linux/amd64}"
+
+echo ">> Using container runtime: $RUNTIME (platform: $PLATFORM)"
+echo ">> Building image $IMAGE_TAG (cached after first run)"
+
+# --layers is the podman/buildah flag for "use the layer cache"; older
+# podman versions default it to false. Docker has caching on by default
+# and rejects the flag, so only pass it for podman.
+declare -a BUILD_ARGS=(--platform "$PLATFORM")
+if [[ "$RUNTIME" != "docker" ]]; then
+ BUILD_ARGS+=(--layers)
+fi
+"$RUNTIME" build "${BUILD_ARGS[@]}" -t "$IMAGE_TAG" -f "$SCRIPT_DIR/Dockerfile" "$SCRIPT_DIR"
+
+# Run as the host user where possible so build outputs are not root-owned.
+declare -a USER_ARGS=()
+if [[ "$RUNTIME" == "docker" ]]; then
+ USER_ARGS=(--user "$(id -u):$(id -g)" -e HOME=/tmp)
+else
+ # Rootless podman maps host UID to container root by default.
+ USER_ARGS=(--userns=keep-id)
+fi
+
+echo ">> Building GAP inside container"
+"$RUNTIME" run --platform "$PLATFORM" --rm \
+ -v "$ROOT_DIR:/gap" \
+ -w /gap \
+ "${USER_ARGS[@]}" \
+ "$IMAGE_TAG" \
+ bash etc/emscripten/build.sh
+
+echo ">> Assembling website"
+bash "$SCRIPT_DIR/assemble-website.sh"
+
+cat </dev/null || sysctl -n hw.ncpu 2>/dev/null || echo 4)
-if ! command -v emmake &> /dev/null; then
- echo Please install, and source, emscripten
- echo This script was tested with version 3.1.23
- echo See https://emscripten.org/docs/getting_started/downloads.html for install instructions
+if ! command -v emmake >/dev/null 2>&1; then
+ echo "Please install and source emscripten." >&2
+ echo "This script is tested with emsdk 3.1.23." >&2
+ echo "See https://emscripten.org/docs/getting_started/downloads.html" >&2
exit 1
-fi;
+fi
# Build the configure script if this is a fresh git checkout
if [[ ! -f ./configure ]]; then
./autogen.sh
fi
-# First build a standard GAP install, for some files
-# we will need during building
+# First build a standard GAP install: we need ffgen and gap-nocomp on the
+# host to generate sources that the wasm build cannot run itself.
+#
+# We copy those generated sources (build/c_*.c, build/ffdata.*) into src/
+# further down, so the wasm build picks them up as overrides. GAP's
+# Makefile.rules, however, also treats src/c_oper1.c, src/ffdata.c etc. as
+# overrides during THIS native build -- so leftovers from a previous run
+# would stop the native build regenerating them in native-build/build/, and
+# the copy below would then fail. Remove any leftovers so the native build
+# regenerates them cleanly (keeps the script idempotent across re-runs).
+rm -f src/c_oper1.c src/c_type1.c src/ffdata.c src/ffdata.h
(
mkdir -p native-build
cd native-build
if [[ ! -f config.status ]]; then
../configure
fi
- make -j8
+ make -j"$JOBS"
)
AUX_BUILD=$PWD/extern/emscripten/build
AUX_PREFIX=$PWD/extern/emscripten/install
-mkdir -p "$AUX_BUILD"
-mkdir -p "$AUX_PREFIX"
+mkdir -p "$AUX_BUILD" "$AUX_PREFIX"
+# A 32-bit build is required by GAP's small-integer representation, so we
+# pin --build to i686-pc-linux-gnu. This may need revisiting if GAP ever
+# moves to a 64-bit-friendly small-integer encoding.
(
mkdir -p "$AUX_BUILD/gmp"
- cd "$AUX_BUILD/gmp" &&
+ cd "$AUX_BUILD/gmp"
if [[ ! -f config.status ]]; then
CC_FOR_BUILD=/usr/bin/gcc ABI=standard \
- emconfigure $BASEDIR/extern/gmp/configure \
- --build i686-pc-linux-gnu --host none \
- --disable-assembly --enable-cxx \
- --prefix=$AUX_PREFIX
- fi &&
- emmake make -j8 &&
+ emconfigure "$BASEDIR/extern/gmp/configure" \
+ --build i686-pc-linux-gnu --host none \
+ --disable-assembly --enable-cxx \
+ --prefix="$AUX_PREFIX"
+ fi
+ emmake make -j"$JOBS"
emmake make install
)
(
mkdir -p "$AUX_BUILD/zlib"
- cd "$AUX_BUILD/zlib" &&
+ cd "$AUX_BUILD/zlib"
if [[ ! -f Makefile ]]; then
- emconfigure $BASEDIR/extern/zlib/configure --prefix=$AUX_PREFIX
- fi;
- emmake make -j8 &&
+ # --static: skip the shared library. Newer emscripten's wasm-ld
+ # rejects linking zlib's .so test programs (examplesh) with
+ # "unknown file type: libz.so"; GAP only needs the static libz.a.
+ emconfigure "$BASEDIR/extern/zlib/configure" --static --prefix="$AUX_PREFIX"
+ fi
+ emmake make -j"$JOBS"
emmake make install
)
-# There are two problems with building GAP
-# 1) GAP builds some executables (ffgen and gap-nocomp), which it wants to
-# execute while building. We get these files from 'native-build'.
-# 2) 'configure' gets confused by some of the LDFLAGS we need, so we have to pass
-# them in to 'make'
+# Two quirks of building GAP under emscripten:
+# 1) GAP runs ffgen and gap-nocomp during the build. We copy the host-built
+# versions in from native-build/ further down.
+# 2) configure rejects some LDFLAGS we need at link time, so we pass them
+# only at make-time.
#
-# These options are:
-# -sASYNCIFY -- we don't care about ASYNC, but this forces the compiler to output
-# all variables onto the stack, which is required for GASMAN
-# Note we could use 'ALLOW_MEMORY_GROWTH', both we don't currently, we instead set
-# a big memory window.
-# -O2 : Some optimisation
-# EXEEXT=.html -- this is actually a GAP makefile option, it lets us make the
-# output 'gap.html', which makes emscripten output a html page we can load
-# --pre-js lazy_fs.js : Prepend lazy_fs.js that is generated for lazy loading
-
-# Run configure if we don't have a makefile, or someone configured this
-# GAP for standard building (emscripten builds will use 'emcc')
-if [[ ! -f GNUmakefile ]] || ! grep '/emcc' GNUmakefile > /dev/null; then
+# Link-time flags worth noting:
+# -sASYNCIFY forces variables onto the stack (required by GASMAN).
+# -O2 enables some optimisation.
+# EXEEXT=.html a GAP makefile knob that produces gap.html, the html
+# shim emscripten generates for loading the wasm module.
+
+if [[ ! -f GNUmakefile ]] || ! grep -q '/emcc' GNUmakefile; then
+ # Wipe any in-tree state from a prior native (or mismatched) build.
+ # Stale build/deps/*.d files reference build/ffdata.h, which under
+ # emcc would be regenerated by a non-executable JS shim; stale .o
+ # files have the wrong architecture. Configure regenerates build/.
+ rm -rf build ffgen
emconfigure ./configure ABI=32 \
- --with-gmp=$AUX_PREFIX \
- --with-zlib=$AUX_PREFIX \
- LDFLAGS="-s ASYNCIFY=1 -O2"
-fi;
+ --with-gmp="$AUX_PREFIX" \
+ --with-zlib="$AUX_PREFIX" \
+ LDFLAGS="-s ASYNCIFY=1 -O2"
+fi
-# Get full required packages
-emmake make bootstrap-pkg-full
+# Provide the GAP package distribution without re-downloading it on every
+# build. Preference order:
+# 1. An existing pkg/ directory.
+# 2. packages.tar.gz already on the host (carried in the source mount).
+# 3. The tarball baked into the docker image at /opt/gap-packages.tar.gz.
+# 4. As a last resort, GAP's own bootstrap-pkg-full target downloads it.
+# Skipping straight to tar avoids `bootstrap-pkg-full`, which calls
+# curl -L -O unconditionally and overwrites packages.tar.gz on every run.
+if [[ ! -d pkg ]]; then
+ if [[ ! -f packages.tar.gz && -f /opt/gap-packages.tar.gz ]]; then
+ cp /opt/gap-packages.tar.gz packages.tar.gz
+ fi
+ if [[ -f packages.tar.gz ]]; then
+ mkdir pkg
+ (cd pkg && tar xzf ../packages.tar.gz)
+ else
+ emmake make bootstrap-pkg-full
+ fi
+fi
-# Copy in files from native_build
+# Copy host-built generated sources into place
cp native-build/build/c_*.c native-build/build/ffdata.* src/
-# Dynamically find and append ALL required files to the JS array
-# The flag -type f is safe because the only symbolic link is 'tst/mockpkg/Makefile.gappkg',
-# which is safe to ignore
-find pkg lib grp tst doc hpcgap dev benchmark -type f | python3 etc/emscripten/generate_gap_fs_json.py
-
-if [ $? -ne 0 ]; then
- echo "Build aborted: generate_gap_fs_json.py failed."
- exit 1
-fi
+# Build the file list that will be served. -L follows symlinks so that
+# users' local development setups (e.g. replacing pkg/foo with a symlink
+# to a git checkout under git/foo) are picked up; -type f then drops any
+# symlinks themselves.
+find -L pkg lib grp tst doc hpcgap dev benchmark -type f ! -path 'pkg/log/*' \
+ | python3 etc/emscripten/generate_gap_fs_json.py
-# The EXEEXT is usually for windows, but here it lets us set GAP's extension,
-# which lets us produce a html page to run GAP in.
-emmake make -j8 LDFLAGS="-lidbfs.js -s ASYNCIFY=1 -sTOTAL_STACK=32mb -sASYNCIFY_STACK_SIZE=32000000 -sINITIAL_MEMORY=2048mb -O2" EXEEXT=".html"
+emmake make -j"$JOBS" \
+ LDFLAGS="-lidbfs.js -s ASYNCIFY=1 -sTOTAL_STACK=32mb -sASYNCIFY_STACK_SIZE=32000000 -sINITIAL_MEMORY=2048mb -O2" \
+ EXEEXT=".html"
diff --git a/etc/emscripten/build_startup_manifest.js b/etc/emscripten/build_startup_manifest.js
deleted file mode 100755
index edb8594b10..0000000000
--- a/etc/emscripten/build_startup_manifest.js
+++ /dev/null
@@ -1,71 +0,0 @@
-#!/usr/bin/env node
-"use strict";
-
-const http = require('http');
-const fs = require('fs');
-const path = require('path');
-
-const PORT = 9999;
-const BASE_DIR = process.cwd();
-const LOG_FILE = path.join(BASE_DIR, 'startup_manifest.json');
-
-const requestedFiles = new Set();
-fs.writeFileSync(LOG_FILE, '[\n]');
-
-const server = http.createServer((req, res) => {
- let urlPath = req.url.split('?')[0];
- if (urlPath === '/') {
- urlPath = '/index.html';
- }
-
- let localDiskPath = urlPath;
- try {
- localDiskPath = decodeURIComponent(urlPath);
- } catch (e) {}
-
- const filePath = path.join(BASE_DIR, localDiskPath);
-
- fs.readFile(filePath, (err, data) => {
- if (err) {
- console.error(`[404] Ignored missing file: ${localDiskPath}`);
- res.writeHead(404);
- res.end(`404: File not found`);
- return;
- }
-
- const ignored = ['/favicon.ico', '/index.html', '/startup_manifest.json', 'coi-serviceworker.js', 'gap-worker.js', 'gap-fs.js', 'gap.js', 'gap.wasm', 'gap-fs.json'];
- if (!ignored.includes(localDiskPath)) {
- let manifestPath = localDiskPath.startsWith('/') ? localDiskPath.substring(1) : localDiskPath;
-
- if (!requestedFiles.has(manifestPath)) {
- requestedFiles.add(manifestPath);
-
- const manifest = Array.from(requestedFiles);
- fs.writeFileSync(LOG_FILE, JSON.stringify(manifest, null, 4));
-
- console.log(`[Loaded & Logged] ${manifestPath} (Total: ${requestedFiles.size})`);
- }
- }
-
- let contentType = 'application/octet-stream';
- if (urlPath.endsWith('.html')) contentType = 'text/html';
- else if (urlPath.endsWith('.js')) contentType = 'text/javascript';
- else if (urlPath.endsWith('.wasm')) contentType = 'application/wasm';
- else if (urlPath.endsWith('.css')) contentType = 'text/css';
-
- res.writeHead(200, {
- 'Content-Type': contentType,
- 'Cross-Origin-Opener-Policy': 'same-origin',
- 'Cross-Origin-Embedder-Policy': 'require-corp',
- 'Access-Control-Allow-Origin': '*'
- });
-
- res.end(data);
- });
-});
-
-server.listen(PORT, '0.0.0.0', () => {
- console.log(`\n Tracker running at http://localhost:${PORT}/`);
- console.log(`Serving files from: ${BASE_DIR}`);
- console.log(`Logging valid loaded files to: ${LOG_FILE}\n`);
-});
diff --git a/etc/emscripten/generate_gap_fs_json.py b/etc/emscripten/generate_gap_fs_json.py
index dbf5447bba..917f0a2a38 100755
--- a/etc/emscripten/generate_gap_fs_json.py
+++ b/etc/emscripten/generate_gap_fs_json.py
@@ -1,18 +1,11 @@
-import sys
-import json
-import os
-
-def main():
- paths = [line.strip() for line in sys.stdin if line.strip()]
+#!/usr/bin/env python3
+"""Read a list of file paths from stdin (one per line) and write them as a
+JSON array to gap-fs.json in the current directory."""
- try:
- with open('gap-fs.json', 'w', encoding='utf-8') as f:
- json.dump(paths, f, separators=(',', ':'))
-
- print(f"Successfully wrote {len(paths)} files to gap-fs.json", file=sys.stderr)
- except Exception as e:
- print(f"Failed to write gap-fs.json: {e}", file=sys.stderr)
- sys.exit(1)
+import json
+import sys
-if __name__ == "__main__":
- main()
+paths = [line.strip() for line in sys.stdin if line.strip()]
+with open("gap-fs.json", "w", encoding="utf-8") as f:
+ json.dump(paths, f, separators=(",", ":"))
+print(f"wrote {len(paths)} files to gap-fs.json", file=sys.stderr)
diff --git a/etc/emscripten/run-web-demo.sh b/etc/emscripten/run-web-demo.sh
deleted file mode 100755
index a82eb948a9..0000000000
--- a/etc/emscripten/run-web-demo.sh
+++ /dev/null
@@ -1,13 +0,0 @@
-#!/usr/bin/env bash
-
-set -eux
-
-echo This script assumes you have already run 'build.sh'
-
-mkdir -p web-example
-cp etc/emscripten/web-template/* web-example/
-cp gap.js gap.wasm gap.worker.js gap-fs.json web-example/
-
-cp -r pkg lib grp tst doc hpcgap dev benchmark web-example/
-cd web-example
-../etc/emscripten/server.rb
diff --git a/etc/emscripten/serve.py b/etc/emscripten/serve.py
new file mode 100755
index 0000000000..7d089f0c54
--- /dev/null
+++ b/etc/emscripten/serve.py
@@ -0,0 +1,35 @@
+#!/usr/bin/env python3
+"""Serve the current directory with the COOP/COEP headers required by
+xterm-pty's SharedArrayBuffer usage. Run from the assembled web-example/
+(or any directory containing the gap.* artifacts).
+
+ ./serve.py # listens on 8080
+ ./serve.py 9000 # listens on 9000
+"""
+
+from __future__ import annotations
+
+import http.server
+import socketserver
+import sys
+
+
+class CrossOriginIsolatedHandler(http.server.SimpleHTTPRequestHandler):
+ def end_headers(self):
+ self.send_header("Cross-Origin-Opener-Policy", "same-origin")
+ self.send_header("Cross-Origin-Embedder-Policy", "require-corp")
+ super().end_headers()
+
+
+def main() -> None:
+ port = int(sys.argv[1]) if len(sys.argv) > 1 else 8080
+ with socketserver.TCPServer(("", port), CrossOriginIsolatedHandler) as httpd:
+ print(f"Serving on http://localhost:{port}/ (Ctrl-C to stop)")
+ try:
+ httpd.serve_forever()
+ except KeyboardInterrupt:
+ print()
+
+
+if __name__ == "__main__":
+ main()
diff --git a/etc/emscripten/server.rb b/etc/emscripten/server.rb
deleted file mode 100755
index 642c9ad167..0000000000
--- a/etc/emscripten/server.rb
+++ /dev/null
@@ -1,15 +0,0 @@
-#!/usr/bin/env ruby
-# Taken from https://github.com/mame/xterm-pty/
-
-require "webrick"
-
-class Server < WEBrick::HTTPServer
- def service(req, res)
- super
- res["Cross-Origin-Opener-Policy"] = "same-origin"
- res["Cross-Origin-Embedder-Policy"] = "require-corp"
- end
-end
-
-Server.new(Port: 8080, DocumentRoot: ".").start
-
diff --git a/etc/emscripten/startup_manifest.json b/etc/emscripten/startup_manifest.json
new file mode 100644
index 0000000000..3ab701c269
--- /dev/null
+++ b/etc/emscripten/startup_manifest.json
@@ -0,0 +1,1521 @@
+[
+ "lib/init.g",
+ "lib/kernel.g",
+ "lib/global.g",
+ "lib/system.g",
+ "lib/read1.g",
+ "lib/hpc/thread1.g",
+ "lib/filter.g",
+ "lib/oper.g",
+ "lib/oper1.g",
+ "lib/type.g",
+ "lib/type1.g",
+ "lib/methsel.g",
+ "lib/methsel2.g",
+ "lib/function.g",
+ "lib/cache.gd",
+ "lib/object.gd",
+ "lib/variable.g",
+ "lib/package.gd",
+ "lib/coll.gd",
+ "lib/list.gd",
+ "lib/wpobj.gd",
+ "lib/arith.gd",
+ "lib/ffe.gd",
+ "lib/domain.gd",
+ "lib/string.g",
+ "lib/cyclotom.g",
+ "lib/set.gd",
+ "lib/record.gd",
+ "lib/random.gd",
+ "lib/cache.gi",
+ "lib/coll.gi",
+ "lib/flag.g",
+ "lib/boolean.g",
+ "lib/ffe.g",
+ "lib/arith.gi",
+ "lib/list.g",
+ "lib/wpobj.g",
+ "lib/permutat.g",
+ "lib/trans.g",
+ "lib/pperm.g",
+ "lib/filter.gi",
+ "lib/object.gi",
+ "lib/listcoef.gd",
+ "lib/info.gd",
+ "lib/files.gd",
+ "lib/streams.gd",
+ "lib/record.gi",
+ "lib/matobj1.gd",
+ "lib/vecmat.gd",
+ "lib/vec8bit.gd",
+ "lib/mat8bit.gd",
+ "lib/global.gd",
+ "lib/info.gi",
+ "lib/global.gi",
+ "lib/options.gd",
+ "lib/options.gi",
+ "lib/attr.gd",
+ "lib/attr.gi",
+ "lib/string.gd",
+ "lib/userpref.g",
+ "lib/cmdledit.g",
+ "lib/cmdleditx.g",
+ "lib/objset.g",
+ "lib/float.gd",
+ "lib/macfloat.g",
+ "lib/hpc/tasks.g",
+ "lib/error.g",
+ "lib/session.g",
+ "lib/read2.g",
+ "lib/process.gd",
+ "lib/files.gi",
+ "lib/streams.gi",
+ "lib/process.gi",
+ "lib/read3.g",
+ "lib/type.gd",
+ "lib/tuples.gd",
+ "lib/rvecempt.gd",
+ "lib/extaset.gd",
+ "lib/extlset.gd",
+ "lib/extrset.gd",
+ "lib/extuset.gd",
+ "lib/dict.gd",
+ "lib/bitfields.gd",
+ "lib/mapping.gd",
+ "lib/mapphomo.gd",
+ "lib/relation.gd",
+ "lib/magma.gd",
+ "lib/mgmideal.gd",
+ "lib/mgmhom.gd",
+ "lib/mgmadj.gd",
+ "lib/mgmcong.gd",
+ "lib/semicong.gd",
+ "lib/semigrp.gd",
+ "lib/smgideal.gd",
+ "lib/monoid.gd",
+ "lib/grp.gd",
+ "lib/invsgp.gd",
+ "lib/addmagma.gd",
+ "lib/addcoset.gd",
+ "lib/semiring.gd",
+ "lib/ring.gd",
+ "lib/matrix.gd",
+ "lib/matint.gd",
+ "lib/matblock.gd",
+ "lib/ideal.gd",
+ "lib/module.gd",
+ "lib/basis.gd",
+ "lib/basismut.gd",
+ "lib/vspc.gd",
+ "lib/vspchom.gd",
+ "lib/zlattice.gd",
+ "lib/algebra.gd",
+ "lib/mgmring.gd",
+ "lib/algfp.gd",
+ "lib/alglie.gd",
+ "lib/algsc.gd",
+ "lib/alghom.gd",
+ "lib/liefam.gd",
+ "lib/algrep.gd",
+ "lib/lierep.gd",
+ "lib/integer.gd",
+ "lib/gaussian.gd",
+ "lib/numtheor.gd",
+ "lib/dlog.gd",
+ "lib/primality.gd",
+ "lib/contfrac.gd",
+ "lib/ringsc.gd",
+ "lib/ringhom.gd",
+ "lib/combinat.gd",
+ "lib/ratfun.gd",
+ "lib/fampred.g",
+ "lib/list.gi",
+ "lib/set.gi",
+ "lib/wpobj.gi",
+ "lib/random.gi",
+ "lib/field.gd",
+ "lib/zmodnz.gd",
+ "lib/zmodnze.gd",
+ "lib/cyclotom.gd",
+ "lib/fldabnum.gd",
+ "lib/padics.gd",
+ "lib/ringpoly.gd",
+ "lib/upoly.gd",
+ "lib/polyfinf.gd",
+ "lib/polyrat.gd",
+ "lib/polyconw.gd",
+ "lib/algfld.gd",
+ "lib/meataxe.gd",
+ "lib/unknown.gd",
+ "lib/word.gd",
+ "lib/wordass.gd",
+ "lib/matobj2.gd",
+ "lib/matobjplist.gd",
+ "lib/matobjnz.gd",
+ "lib/rws.gd",
+ "lib/rwspcclt.gd",
+ "lib/rwsgrp.gd",
+ "lib/rwspcgrp.gd",
+ "lib/groebner.gd",
+ "lib/pcgs.gd",
+ "lib/pcgsind.gd",
+ "lib/pcgspcg.gd",
+ "lib/pcgsmodu.gd",
+ "lib/pcgsperm.gd",
+ "lib/pcgsspec.gd",
+ "lib/grppc.gd",
+ "lib/grppcnrm.gd",
+ "lib/grptbl.gd",
+ "lib/grpperm.gd",
+ "lib/grpprmcs.gd",
+ "lib/stbcbckt.gd",
+ "lib/ghom.gd",
+ "lib/ghompcgs.gd",
+ "lib/gprd.gd",
+ "lib/ghomperm.gd",
+ "lib/gpprmsya.gd",
+ "lib/addgphom.gd",
+ "lib/grpnames.g",
+ "lib/grpnames.gd",
+ "lib/quotsys.gd",
+ "lib/pquot.gd",
+ "lib/oprt.gd",
+ "lib/partitio.gd",
+ "lib/stbc.gd",
+ "lib/clas.gd",
+ "lib/clashom.gd",
+ "lib/permdeco.gd",
+ "lib/csetgrp.gd",
+ "lib/factgrp.gd",
+ "lib/grpreps.gd",
+ "lib/grppcrep.gd",
+ "lib/onecohom.gd",
+ "lib/grppccom.gd",
+ "lib/twocohom.gd",
+ "lib/grppcext.gd",
+ "lib/grppcfp.gd",
+ "lib/randiso.gd",
+ "lib/schur.gd",
+ "lib/schursym.gd",
+ "lib/grplatt.gd",
+ "lib/oprtglat.gd",
+ "lib/grppclat.gd",
+ "lib/grppcaut.gd",
+ "lib/straight.gd",
+ "lib/memory.gd",
+ "lib/grpfp.gd",
+ "lib/grpfree.gd",
+ "lib/sgpres.gd",
+ "lib/tietze.gd",
+ "lib/ghomfp.gd",
+ "lib/dt.g",
+ "lib/integer.gi",
+ "lib/grpnice.gd",
+ "lib/morpheus.gd",
+ "lib/grpmat.gd",
+ "lib/fitfree.gd",
+ "lib/grpffmat.gd",
+ "lib/grpramat.gd",
+ "grp/basic.gd",
+ "grp/classic.gd",
+ "grp/conformal.gd",
+ "grp/perf.gd",
+ "grp/suzuki.gd",
+ "grp/ree.gd",
+ "grp/simple.gd",
+ "grp/imf.gd",
+ "grp/glzmodmz.gd",
+ "grp/clasmax.grp",
+ "lib/orders.gd",
+ "lib/trans.gd",
+ "lib/pperm.gd",
+ "lib/fastendo.gd",
+ "lib/fpsemi.gd",
+ "lib/fpmon.gd",
+ "lib/rwssmg.gd",
+ "lib/kbsemi.gd",
+ "lib/tcsemi.gd",
+ "lib/adjoin.gd",
+ "lib/semirel.gd",
+ "lib/semitran.gd",
+ "lib/reesmat.gd",
+ "lib/semiquo.gd",
+ "lib/semipperm.gd",
+ "lib/pager.gd",
+ "lib/helpbase.gd",
+ "lib/helpview.gd",
+ "lib/helpt2t.gd",
+ "lib/helpdef.gd",
+ "lib/ctbl.gd",
+ "lib/ctblfuns.gd",
+ "lib/ctblmaps.gd",
+ "lib/ctblauto.gd",
+ "lib/ctbllatt.gd",
+ "lib/ctblsymm.gd",
+ "lib/ctblsolv.gd",
+ "lib/ctblpope.gd",
+ "lib/ctblmoli.gd",
+ "lib/ctblmono.gd",
+ "lib/ctblgrp.gd",
+ "lib/tom.gd",
+ "lib/proto.gd",
+ "lib/gasman.gd",
+ "lib/memusage.gd",
+ "lib/read4.g",
+ "lib/profile.g",
+ "lib/newprofile.g",
+ "lib/methwhy.g",
+ "lib/pager.gi",
+ "lib/helpbase.gi",
+ "lib/helpview.gi",
+ "lib/helpt2t.gi",
+ "lib/helpdef.gi",
+ "lib/reread.g",
+ "lib/package.gi",
+ "lib/string.gi",
+ "lib/test.gd",
+ "lib/test.gi",
+ "lib/galois.gd",
+ "lib/galois.gi",
+ "lib/transatl.g",
+ "lib/obsolete.g",
+ "lib/obsolete.gd",
+ "lib/read.g",
+ "lib/read5.g",
+ "lib/type.gi",
+ "lib/rvecempt.gi",
+ "lib/ratfun1.gi",
+ "lib/matrix.gi",
+ "lib/matint.gi",
+ "lib/matblock.gi",
+ "lib/tuples.gi",
+ "lib/domain.gi",
+ "lib/mapping1.gi",
+ "lib/mapping.gi",
+ "lib/mapprep.gi",
+ "lib/mapphomo.gi",
+ "lib/relation.gi",
+ "lib/magma.gi",
+ "lib/mgmideal.gi",
+ "lib/mgmhom.gi",
+ "lib/mgmadj.gi",
+ "lib/mgmcong.gi",
+ "lib/semigrp.gi",
+ "lib/semicong.gi",
+ "lib/smgideal.gi",
+ "lib/monoid.gi",
+ "lib/grp.gi",
+ "lib/invsgp.gi",
+ "lib/addmagma.gi",
+ "lib/addcoset.gi",
+ "lib/ring.gi",
+ "lib/ideal.gi",
+ "lib/module.gi",
+ "lib/modfree.gi",
+ "lib/modulrow.gi",
+ "lib/modulmat.gi",
+ "lib/basis.gi",
+ "lib/basismut.gi",
+ "lib/vspc.gi",
+ "lib/vspcrow.gi",
+ "lib/vspcmat.gi",
+ "lib/vspchom.gi",
+ "lib/zlattice.gi",
+ "lib/mgmring.gi",
+ "lib/algebra.gi",
+ "lib/idealalg.gi",
+ "lib/alghom.gi",
+ "lib/algfp.gi",
+ "lib/alglie.gi",
+ "lib/algliess.gi",
+ "lib/algsc.gi",
+ "lib/algmat.gi",
+ "lib/liefam.gi",
+ "lib/algrep.gi",
+ "lib/lierep.gi",
+ "lib/numtheor.gi",
+ "lib/dlog.gi",
+ "lib/primality.gi",
+ "lib/contfrac.gi",
+ "lib/ringsc.gi",
+ "lib/ringhom.gi",
+ "lib/combinat.gi",
+ "lib/ratfun.gi",
+ "lib/ratfunul.gi",
+ "lib/ringpoly.gi",
+ "lib/upoly.gi",
+ "lib/upolyirr.gi",
+ "lib/polyfinf.gi",
+ "lib/polyrat.gi",
+ "lib/polyconw.gi",
+ "lib/listcoef.gi",
+ "lib/algfld.gi",
+ "lib/groebner.gi",
+ "lib/unknown.gi",
+ "lib/field.gi",
+ "lib/fieldfin.gi",
+ "lib/zmodnz.gi",
+ "lib/zmodnze.gi",
+ "lib/ffe.gi",
+ "lib/ffeconway.gi",
+ "lib/rational.gi",
+ "lib/gaussian.gi",
+ "lib/cyclotom.gi",
+ "lib/fldabnum.gi",
+ "lib/padics.gi",
+ "lib/matobj.gi",
+ "lib/matobjrowlist.gi",
+ "lib/vecmat.gi",
+ "lib/vec8bit.gi",
+ "lib/mat8bit.gi",
+ "lib/matobjplist.gi",
+ "lib/matobjnz.gi",
+ "lib/meataxe.gi",
+ "lib/meatauto.gi",
+ "lib/word.gi",
+ "lib/wordass.gi",
+ "lib/wordrep.gi",
+ "lib/wordlett.gi",
+ "lib/mgmfree.gi",
+ "lib/smgrpfre.gi",
+ "lib/monofree.gi",
+ "lib/grpfree.gi",
+ "lib/rws.gi",
+ "lib/rwspcclt.gi",
+ "lib/rwspcsng.gi",
+ "lib/rwspccoc.gi",
+ "lib/rwsgrp.gi",
+ "lib/rwspcgrp.gi",
+ "lib/rwsdt.gi",
+ "lib/nilpquot.gi",
+ "lib/pquot.gi",
+ "lib/pcgs.gi",
+ "lib/pcgsind.gi",
+ "lib/pcgsmodu.gi",
+ "lib/pcgspcg.gi",
+ "lib/pcgscomp.gi",
+ "lib/pcgsperm.gi",
+ "lib/pcgsnice.gi",
+ "lib/pcgsspec.gi",
+ "lib/grppc.gi",
+ "lib/grppcint.gi",
+ "lib/grppcprp.gi",
+ "lib/grppcatr.gi",
+ "lib/grppcnrm.gi",
+ "lib/bitfields.gi",
+ "lib/dict.gi",
+ "lib/dicthf.gi",
+ "lib/grptbl.gi",
+ "lib/ghom.gi",
+ "lib/ghompcgs.gi",
+ "lib/gprd.gi",
+ "lib/ghomperm.gi",
+ "lib/grpperm.gi",
+ "lib/gpprmsya.gi",
+ "lib/gprdperm.gi",
+ "lib/gprdpc.gi",
+ "lib/gprdmat.gi",
+ "lib/oprt.gi",
+ "lib/oprtperm.gi",
+ "lib/oprtpcgs.gi",
+ "lib/partitio.gi",
+ "lib/stbc.gi",
+ "lib/stbcbckt.gi",
+ "lib/stbcrand.gi",
+ "lib/clas.gi",
+ "lib/claspcgs.gi",
+ "lib/csetgrp.gi",
+ "lib/csetperm.gi",
+ "lib/csetpc.gi",
+ "lib/factgrp.gi",
+ "lib/grpreps.gi",
+ "lib/grppcrep.gi",
+ "lib/grpprmcs.gi",
+ "lib/grpnames.gi",
+ "lib/onecohom.gi",
+ "lib/grppccom.gi",
+ "lib/grpcompl.gi",
+ "lib/twocohom.gi",
+ "lib/grppcext.gi",
+ "lib/randiso.gi",
+ "lib/randiso2.gi",
+ "lib/grppcfp.gi",
+ "lib/schur.gi",
+ "lib/schursym.gi",
+ "lib/grpnice.gi",
+ "lib/fitfree.gi",
+ "lib/permdeco.gi",
+ "lib/clashom.gi",
+ "lib/clasperm.gi",
+ "lib/maxsub.gi",
+ "lib/norad.gi",
+ "lib/autsr.gi",
+ "lib/morpheus.gi",
+ "lib/grplatt.gi",
+ "lib/oprtglat.gi",
+ "lib/grppclat.gi",
+ "lib/grppcaut.gi",
+ "lib/grpmat.gi",
+ "lib/grpffmat.gi",
+ "lib/grpramat.gi",
+ "lib/grpfp.gi",
+ "lib/gpfpiso.gi",
+ "lib/sgpres.gi",
+ "lib/tietze.gi",
+ "lib/ghomfp.gi",
+ "lib/addgphom.gi",
+ "lib/trans.gi",
+ "lib/pperm.gi",
+ "lib/fastendo.gi",
+ "lib/fpsemi.gi",
+ "lib/fpmon.gi",
+ "lib/rwssmg.gi",
+ "lib/kbsemi.gi",
+ "lib/tcsemi.gi",
+ "lib/adjoin.gi",
+ "lib/semirel.gi",
+ "lib/semitran.gi",
+ "lib/reesmat.gi",
+ "lib/semiquo.gi",
+ "lib/semipperm.gi",
+ "lib/proto.gi",
+ "lib/orders.gi",
+ "lib/gasman.gi",
+ "lib/memusage.gi",
+ "lib/function.gi",
+ "lib/float.gi",
+ "lib/ieee754.g",
+ "lib/read6.g",
+ "grp/basicpcg.gi",
+ "grp/basicprm.gi",
+ "grp/basicmat.gi",
+ "grp/basicfp.gi",
+ "grp/perf.grp",
+ "grp/classic.gi",
+ "grp/conformal.gi",
+ "grp/suzuki.gi",
+ "grp/ree.gi",
+ "grp/simple.gi",
+ "grp/imf.grp",
+ "grp/imf.gi",
+ "grp/glzmodmz.gi",
+ "lib/read7.g",
+ "lib/ctbl.gi",
+ "lib/ctblfuns.gi",
+ "lib/ctblmaps.gi",
+ "lib/ctblauto.gi",
+ "lib/ctbllatt.gi",
+ "lib/ctblsymm.gi",
+ "lib/ctblsolv.gi",
+ "lib/ctblpope.gi",
+ "lib/ctblmoli.gi",
+ "lib/ctblmono.gi",
+ "lib/ctblgrp.gi",
+ "lib/ctblperm.gi",
+ "lib/ctblpc.gi",
+ "lib/tom.gi",
+ "lib/straight.gi",
+ "lib/memory.gi",
+ "lib/read8.g",
+ "lib/overload.g",
+ "lib/syntaxtree.gd",
+ "lib/syntaxtree.gi",
+ "lib/teaching.g",
+ "lib/teachm2.g",
+ "lib/operdebug.g",
+ "lib/colorprompt.g",
+ "pkg/4ti2interface/PackageInfo.g",
+ "pkg/ace/PackageInfo.g",
+ "pkg/aclib/PackageInfo.g",
+ "pkg/agt/PackageInfo.g",
+ "pkg/alco/PackageInfo.g",
+ "pkg/alnuth/PackageInfo.g",
+ "pkg/anupq/PackageInfo.g",
+ "pkg/atlasrep/PackageInfo.g",
+ "pkg/autodoc/PackageInfo.g",
+ "pkg/automata/PackageInfo.g",
+ "pkg/automgrp/PackageInfo.g",
+ "pkg/autpgrp/PackageInfo.g",
+ "pkg/browse/PackageInfo.g",
+ "pkg/cap/PackageInfo.g",
+ "pkg/caratinterface/PackageInfo.g",
+ "pkg/cddinterface/PackageInfo.g",
+ "pkg/circle/PackageInfo.g",
+ "pkg/classicalmaximals/PackageInfo.g",
+ "pkg/classicpres/PackageInfo.g",
+ "pkg/cohomolo/PackageInfo.g",
+ "pkg/congruence/PackageInfo.g",
+ "pkg/corefreesub/PackageInfo.g",
+ "pkg/corelg/PackageInfo.g",
+ "pkg/crime/PackageInfo.g",
+ "pkg/crisp/PackageInfo.g",
+ "pkg/crypting/PackageInfo.g",
+ "pkg/cryst/PackageInfo.g",
+ "pkg/crystcat/PackageInfo.g",
+ "pkg/ctbllib/PackageInfo.g",
+ "pkg/cubefree/PackageInfo.g",
+ "pkg/curlinterface/PackageInfo.g",
+ "pkg/cvec/PackageInfo.g",
+ "pkg/datastructures/PackageInfo.g",
+ "pkg/deepthought/PackageInfo.g",
+ "pkg/design/PackageInfo.g",
+ "pkg/difsets/PackageInfo.g",
+ "pkg/digraphs/PackageInfo.g",
+ "pkg/edim/PackageInfo.g",
+ "pkg/example/PackageInfo.g",
+ "pkg/examplesforhomalg/PackageInfo.g",
+ "pkg/factint/PackageInfo.g",
+ "pkg/ferret/PackageInfo.g",
+ "pkg/fga/PackageInfo.g",
+ "pkg/fining/PackageInfo.g",
+ "pkg/float/PackageInfo.g",
+ "pkg/format/PackageInfo.g",
+ "pkg/forms/PackageInfo.g",
+ "pkg/fplsa/PackageInfo.g",
+ "pkg/fr/PackageInfo.g",
+ "pkg/francy/PackageInfo.g",
+ "pkg/fwtree/PackageInfo.g",
+ "pkg/gapdoc/PackageInfo.g",
+ "pkg/gauss/PackageInfo.g",
+ "pkg/gaussforhomalg/PackageInfo.g",
+ "pkg/gbnp/PackageInfo.g",
+ "pkg/generalizedmorphismsforcap/PackageInfo.g",
+ "pkg/genss/PackageInfo.g",
+ "pkg/gradedmodules/PackageInfo.g",
+ "pkg/gradedringforhomalg/PackageInfo.g",
+ "pkg/grape/PackageInfo.g",
+ "pkg/groupoids/PackageInfo.g",
+ "pkg/grpconst/PackageInfo.g",
+ "pkg/guarana/PackageInfo.g",
+ "pkg/guava/PackageInfo.g",
+ "pkg/hap/PackageInfo.g",
+ "pkg/hapcryst/PackageInfo.g",
+ "pkg/hecke/PackageInfo.g",
+ "pkg/help/PackageInfo.g",
+ "pkg/homalg/PackageInfo.g",
+ "pkg/homalgtocas/PackageInfo.g",
+ "pkg/ibnp/PackageInfo.g",
+ "pkg/idrel/PackageInfo.g",
+ "pkg/images/PackageInfo.g",
+ "pkg/inducereduce/PackageInfo.g",
+ "pkg/intpic/PackageInfo.g",
+ "pkg/io/PackageInfo.g",
+ "pkg/io_forhomalg/PackageInfo.g",
+ "pkg/irredsol/PackageInfo.g",
+ "pkg/itc/PackageInfo.g",
+ "pkg/json/PackageInfo.g",
+ "pkg/jupyterkernel/PackageInfo.g",
+ "pkg/jupyterviz/PackageInfo.g",
+ "pkg/kan/PackageInfo.g",
+ "pkg/kbmag/PackageInfo.g",
+ "pkg/laguna/PackageInfo.g",
+ "pkg/liealgdb/PackageInfo.g",
+ "pkg/liepring/PackageInfo.g",
+ "pkg/liering/PackageInfo.g",
+ "pkg/linearalgebraforcap/PackageInfo.g",
+ "pkg/lins/PackageInfo.g",
+ "pkg/localizeringforhomalg/PackageInfo.g",
+ "pkg/localnr/PackageInfo.g",
+ "pkg/loops/PackageInfo.g",
+ "pkg/lpres/PackageInfo.g",
+ "pkg/majoranaalgebras/PackageInfo.g",
+ "pkg/mapclass/PackageInfo.g",
+ "pkg/matgrp/PackageInfo.g",
+ "pkg/matricesforhomalg/PackageInfo.g",
+ "pkg/modisom/PackageInfo.g",
+ "pkg/modulargroup/PackageInfo.g",
+ "pkg/modulepresentationsforcap/PackageInfo.g",
+ "pkg/modules/PackageInfo.g",
+ "pkg/monoidalcategories/PackageInfo.g",
+ "pkg/nconvex/PackageInfo.g",
+ "pkg/nilmat/PackageInfo.g",
+ "pkg/nock/PackageInfo.g",
+ "pkg/nofoma/PackageInfo.g",
+ "pkg/normalizinterface/PackageInfo.g",
+ "pkg/nq/PackageInfo.g",
+ "pkg/numericalsgps/PackageInfo.g",
+ "pkg/openmath/PackageInfo.g",
+ "pkg/orb/PackageInfo.g",
+ "pkg/origami/PackageInfo.g",
+ "pkg/packagemaker/PackageInfo.g",
+ "pkg/packagemanager/PackageInfo.g",
+ "pkg/patternclass/PackageInfo.g",
+ "pkg/permut/PackageInfo.g",
+ "pkg/polenta/PackageInfo.g",
+ "pkg/polycyclic/PackageInfo.g",
+ "pkg/polymaking/PackageInfo.g",
+ "pkg/primgrp/PackageInfo.g",
+ "pkg/profiling/PackageInfo.g",
+ "pkg/qdistrnd/PackageInfo.g",
+ "pkg/qpa/PackageInfo.g",
+ "pkg/quagroup/PackageInfo.g",
+ "pkg/radiroot/PackageInfo.g",
+ "pkg/rcwa/PackageInfo.g",
+ "pkg/rds/PackageInfo.g",
+ "pkg/recog/PackageInfo.g",
+ "pkg/repndecomp/PackageInfo.g",
+ "pkg/repsn/PackageInfo.g",
+ "pkg/resclasses/PackageInfo.g",
+ "pkg/ringsforhomalg/PackageInfo.g",
+ "pkg/sco/PackageInfo.g",
+ "pkg/scscp/PackageInfo.g",
+ "pkg/semigroups/PackageInfo.g",
+ "pkg/sglppow/PackageInfo.g",
+ "pkg/sgpviz/PackageInfo.g",
+ "pkg/simpcomp/PackageInfo.g",
+ "pkg/singular/PackageInfo.g",
+ "pkg/sl2reps/PackageInfo.g",
+ "pkg/sla/PackageInfo.g",
+ "pkg/smallantimagmas/PackageInfo.g",
+ "pkg/smallclassnr/PackageInfo.g",
+ "pkg/smallgrp/PackageInfo.g",
+ "pkg/smallsemi/PackageInfo.g",
+ "pkg/sonata/PackageInfo.g",
+ "pkg/sophus/PackageInfo.g",
+ "pkg/sotgrps/PackageInfo.g",
+ "pkg/spinsym/PackageInfo.g",
+ "pkg/standardff/PackageInfo.g",
+ "pkg/symbcompcc/PackageInfo.g",
+ "pkg/thelma/PackageInfo.g",
+ "pkg/tomlib/PackageInfo.g",
+ "pkg/toolsforhomalg/PackageInfo.g",
+ "pkg/toric/PackageInfo.g",
+ "pkg/transgrp/PackageInfo.g",
+ "pkg/twistedconjugacy/PackageInfo.g",
+ "pkg/typeset/PackageInfo.g",
+ "pkg/ugaly/PackageInfo.g",
+ "pkg/unipot/PackageInfo.g",
+ "pkg/unitlib/PackageInfo.g",
+ "pkg/utils/PackageInfo.g",
+ "pkg/uuid/PackageInfo.g",
+ "pkg/walrus/PackageInfo.g",
+ "pkg/wedderga/PackageInfo.g",
+ "pkg/wpe/PackageInfo.g",
+ "pkg/xgap/PackageInfo.g",
+ "pkg/xmod/PackageInfo.g",
+ "pkg/xmodalg/PackageInfo.g",
+ "pkg/yangbaxter/PackageInfo.g",
+ "pkg/zeromqinterface/PackageInfo.g",
+ "pkg/gapdoc/init.g",
+ "pkg/gapdoc/lib/UnicodeTools.gd",
+ "pkg/gapdoc/lib/PrintUtil.gd",
+ "pkg/gapdoc/lib/Text.gd",
+ "pkg/gapdoc/lib/ComposeXML.gd",
+ "pkg/gapdoc/lib/XMLParser.gd",
+ "pkg/gapdoc/lib/GAPDoc.gd",
+ "pkg/gapdoc/lib/BibTeX.gd",
+ "pkg/gapdoc/lib/BibXMLextTools.gd",
+ "pkg/gapdoc/lib/GAPDoc2LaTeX.gd",
+ "pkg/gapdoc/lib/GAPDoc2Text.gd",
+ "pkg/gapdoc/lib/GAPDoc2HTML.gd",
+ "pkg/gapdoc/lib/Make.g",
+ "pkg/gapdoc/lib/Examples.gd",
+ "pkg/gapdoc/read.g",
+ "pkg/gapdoc/lib/UnicodeTools.gi",
+ "pkg/gapdoc/lib/UnicodeTabs.g",
+ "pkg/gapdoc/lib/PrintUtil.gi",
+ "pkg/gapdoc/lib/Text.gi",
+ "pkg/gapdoc/lib/ComposeXML.gi",
+ "pkg/gapdoc/lib/XMLParser.gi",
+ "pkg/gapdoc/lib/gapdocdtdinfo.g",
+ "pkg/gapdoc/lib/GAPDoc.gi",
+ "pkg/gapdoc/lib/BibTeX.gi",
+ "pkg/gapdoc/lib/bibxmlextinfo.g",
+ "pkg/gapdoc/lib/BibXMLextTools.gi",
+ "pkg/gapdoc/lib/GAPDoc2LaTeX.gi",
+ "pkg/gapdoc/lib/latexhead.tex",
+ "pkg/gapdoc/lib/GAPDoc2Text.gi",
+ "pkg/gapdoc/lib/TextThemes.g",
+ "pkg/gapdoc/lib/GAPDoc2HTML.gi",
+ "pkg/gapdoc/lib/Examples.gi",
+ "pkg/gapdoc/lib/HelpBookHandler.g",
+ "pkg/primgrp/init.g",
+ "pkg/primgrp/lib/primitiv.gd",
+ "pkg/primgrp/lib/irredsol.gd",
+ "pkg/primgrp/read.g",
+ "pkg/primgrp/lib/primitiv.grp",
+ "pkg/primgrp/lib/primitiv.gi",
+ "pkg/primgrp/lib/irredsol.grp",
+ "pkg/primgrp/lib/irredsol.gi",
+ "pkg/primgrp/lib/cohorts.grp",
+ "pkg/smallgrp/init.g",
+ "pkg/smallgrp/gap/small.gd",
+ "pkg/smallgrp/read.g",
+ "pkg/smallgrp/gap/small.gi",
+ "pkg/smallgrp/gap/smlgp1.g",
+ "pkg/smallgrp/gap/idgrp1.g",
+ "pkg/smallgrp/gap/smlinfo.gi",
+ "pkg/smallgrp/small2/smlgp2.g.gz",
+ "pkg/smallgrp/small3/smlgp3.g.gz",
+ "pkg/smallgrp/small4/smlgp4.g.gz",
+ "pkg/smallgrp/small5/smlgp5.g.gz",
+ "pkg/smallgrp/small6/smlgp6.g.gz",
+ "pkg/smallgrp/small7/smlgp7.g.gz",
+ "pkg/smallgrp/small8/smlgp8.g.gz",
+ "pkg/smallgrp/small9/smlgp9.g.gz",
+ "pkg/smallgrp/small10/smlgp10.g.gz",
+ "pkg/smallgrp/small11/smlgp11.g.gz",
+ "pkg/smallgrp/id2/idgrp2.g.gz",
+ "pkg/smallgrp/id3/idgrp3.g.gz",
+ "pkg/smallgrp/id4/idgrp4.g.gz",
+ "pkg/smallgrp/id5/idgrp5.g.gz",
+ "pkg/smallgrp/id6/idgrp6.g.gz",
+ "pkg/smallgrp/id9/idgrp9.g.gz",
+ "pkg/smallgrp/id10/idgrp10.g.gz",
+ "pkg/transgrp/init.g",
+ "pkg/transgrp/lib/trans.gd",
+ "pkg/transgrp/read.g",
+ "pkg/transgrp/lib/trans.grp",
+ "pkg/transgrp/lib/trans.gi",
+ "pkg/autpgrp/init.g",
+ "pkg/autpgrp/gap/autos.gd",
+ "pkg/autpgrp/read.g",
+ "pkg/autpgrp/gap/general.gi",
+ "pkg/autpgrp/gap/autoops.gi",
+ "pkg/autpgrp/gap/matrix.gi",
+ "pkg/autpgrp/gap/nicestab.gi",
+ "pkg/autpgrp/gap/initmat.gi",
+ "pkg/autpgrp/gap/initperm.gi",
+ "pkg/autpgrp/gap/hybrstab.gi",
+ "pkg/autpgrp/gap/matrstab.gi",
+ "pkg/autpgrp/gap/orbstab.gi",
+ "pkg/autpgrp/gap/autos.gi",
+ "pkg/autpgrp/gap/pcpres.gi",
+ "pkg/autpgrp/gap/countcl.gi",
+ "pkg/alnuth/init.g",
+ "pkg/alnuth/gap/setup.gd",
+ "pkg/alnuth/gap/factors.gd",
+ "pkg/alnuth/gap/field.gd",
+ "pkg/polycyclic/init.g",
+ "pkg/polycyclic/gap/matrix/matrix.gd",
+ "pkg/polycyclic/gap/basic/infos.gd",
+ "pkg/polycyclic/gap/basic/collect.gd",
+ "pkg/polycyclic/gap/basic/pcpelms.gd",
+ "pkg/polycyclic/gap/basic/pcpgrps.gd",
+ "pkg/polycyclic/gap/basic/pcppcps.gd",
+ "pkg/polycyclic/gap/basic/grphoms.gd",
+ "pkg/polycyclic/gap/basic/basic.gd",
+ "pkg/polycyclic/gap/cohom/cohom.gd",
+ "pkg/polycyclic/gap/matrep/matrep.gd",
+ "pkg/polycyclic/gap/matrep/unitri.gd",
+ "pkg/polycyclic/gap/pcpgrp/pcpgrp.gd",
+ "pkg/polycyclic/gap/pcpgrp/torsion.gd",
+ "pkg/polycyclic/gap/exam/exam.gd",
+ "pkg/polycyclic/gap/obsolete.gd",
+ "pkg/alnuth/read.g",
+ "pkg/alnuth/gap/userpref.gi",
+ "pkg/alnuth/gap/setup.gi",
+ "pkg/alnuth/gap/pari.gi",
+ "pkg/alnuth/gap/factors.gi",
+ "pkg/alnuth/gap/matfield.gi",
+ "pkg/alnuth/gap/polfield.gi",
+ "pkg/alnuth/gap/field.gi",
+ "pkg/alnuth/gap/unithom.gi",
+ "pkg/alnuth/gap/matunits.gi",
+ "pkg/alnuth/gap/rels.gi",
+ "pkg/alnuth/gap/present.gi",
+ "pkg/alnuth/gap/isom.gi",
+ "pkg/alnuth/gap/rationals.gi",
+ "pkg/alnuth/exam/unimod.gi",
+ "pkg/alnuth/exam/rationals.gi",
+ "pkg/alnuth/exam/fields.gi",
+ "pkg/polycyclic/read.g",
+ "pkg/polycyclic/gap/matrix/rowbases.gi",
+ "pkg/polycyclic/gap/matrix/latbases.gi",
+ "pkg/polycyclic/gap/matrix/lattices.gi",
+ "pkg/polycyclic/gap/matrix/modules.gi",
+ "pkg/polycyclic/gap/matrix/triangle.gi",
+ "pkg/polycyclic/gap/matrix/hnf.gi",
+ "pkg/polycyclic/gap/basic/collect.gi",
+ "pkg/polycyclic/gap/basic/colftl.gi",
+ "pkg/polycyclic/gap/basic/colcom.gi",
+ "pkg/polycyclic/gap/basic/coldt.gi",
+ "pkg/polycyclic/gap/basic/colsave.gi",
+ "pkg/polycyclic/gap/basic/pcpelms.gi",
+ "pkg/polycyclic/gap/basic/pcppcps.gi",
+ "pkg/polycyclic/gap/basic/pcpgrps.gi",
+ "pkg/polycyclic/gap/basic/pcppara.gi",
+ "pkg/polycyclic/gap/basic/pcpexpo.gi",
+ "pkg/polycyclic/gap/basic/pcpsers.gi",
+ "pkg/polycyclic/gap/basic/grphoms.gi",
+ "pkg/polycyclic/gap/basic/pcpfact.gi",
+ "pkg/polycyclic/gap/basic/chngpcp.gi",
+ "pkg/polycyclic/gap/basic/convert.gi",
+ "pkg/polycyclic/gap/basic/orbstab.gi",
+ "pkg/polycyclic/gap/basic/construct.gi",
+ "pkg/polycyclic/gap/cohom/cohom.gi",
+ "pkg/polycyclic/gap/cohom/addgrp.gi",
+ "pkg/polycyclic/gap/cohom/general.gi",
+ "pkg/polycyclic/gap/cohom/solabel.gi",
+ "pkg/polycyclic/gap/cohom/solcohom.gi",
+ "pkg/polycyclic/gap/cohom/twocohom.gi",
+ "pkg/polycyclic/gap/cohom/intcohom.gi",
+ "pkg/polycyclic/gap/cohom/onecohom.gi",
+ "pkg/polycyclic/gap/cohom/grpext.gi",
+ "pkg/polycyclic/gap/cohom/grpcom.gi",
+ "pkg/polycyclic/gap/cohom/norcom.gi",
+ "pkg/polycyclic/gap/action/extend.gi",
+ "pkg/polycyclic/gap/action/basepcgs.gi",
+ "pkg/polycyclic/gap/action/freegens.gi",
+ "pkg/polycyclic/gap/action/dixon.gi",
+ "pkg/polycyclic/gap/action/kernels.gi",
+ "pkg/polycyclic/gap/action/orbstab.gi",
+ "pkg/polycyclic/gap/action/orbnorm.gi",
+ "pkg/polycyclic/gap/pcpgrp/general.gi",
+ "pkg/polycyclic/gap/pcpgrp/inters.gi",
+ "pkg/polycyclic/gap/pcpgrp/grpinva.gi",
+ "pkg/polycyclic/gap/pcpgrp/torsion.gi",
+ "pkg/polycyclic/gap/pcpgrp/maxsub.gi",
+ "pkg/polycyclic/gap/pcpgrp/findex.gi",
+ "pkg/polycyclic/gap/pcpgrp/nindex.gi",
+ "pkg/polycyclic/gap/pcpgrp/nilpot.gi",
+ "pkg/polycyclic/gap/pcpgrp/polyz.gi",
+ "pkg/polycyclic/gap/pcpgrp/pcpattr.gi",
+ "pkg/polycyclic/gap/pcpgrp/wreath.gi",
+ "pkg/polycyclic/gap/pcpgrp/fitting.gi",
+ "pkg/polycyclic/gap/pcpgrp/centcon.gi",
+ "pkg/polycyclic/gap/pcpgrp/normcon.gi",
+ "pkg/polycyclic/gap/pcpgrp/schur.gi",
+ "pkg/polycyclic/gap/pcpgrp/tensor.gi",
+ "pkg/polycyclic/gap/matrep/matrep.gi",
+ "pkg/polycyclic/gap/matrep/affine.gi",
+ "pkg/polycyclic/gap/matrep/unitri.gi",
+ "pkg/polycyclic/gap/exam/pcplib.gi",
+ "pkg/polycyclic/gap/exam/matlib.gi",
+ "pkg/polycyclic/gap/exam/nqlib.gi",
+ "pkg/polycyclic/gap/exam/generic.gi",
+ "pkg/polycyclic/gap/exam/bgnilp.gi",
+ "pkg/polycyclic/gap/exam/metacyc.gi",
+ "pkg/polycyclic/gap/exam/metagrp.gi",
+ "pkg/polycyclic/gap/cover/const/bas.gi",
+ "pkg/polycyclic/gap/cover/const/orb.gi",
+ "pkg/polycyclic/gap/cover/const/aut.gi",
+ "pkg/polycyclic/gap/cover/const/com.gi",
+ "pkg/polycyclic/gap/cover/const/cov.gi",
+ "pkg/crisp/init.g",
+ "pkg/crisp/lib/classes.gd",
+ "pkg/crisp/lib/grpclass.gd",
+ "pkg/crisp/lib/fitting.gd",
+ "pkg/crisp/lib/schunck.gd",
+ "pkg/crisp/lib/form.gd",
+ "pkg/crisp/lib/projector.gd",
+ "pkg/crisp/lib/injector.gd",
+ "pkg/crisp/lib/normpro.gd",
+ "pkg/crisp/lib/solveeq.gd",
+ "pkg/crisp/lib/compl.gd",
+ "pkg/crisp/lib/radical.gd",
+ "pkg/crisp/lib/residual.gd",
+ "pkg/crisp/lib/util.gd",
+ "pkg/crisp/lib/samples.gd",
+ "pkg/crisp/lib/socle.gd",
+ "pkg/crisp/read.g",
+ "pkg/crisp/lib/classes.gi",
+ "pkg/crisp/lib/grpclass.gi",
+ "pkg/crisp/lib/fitting.gi",
+ "pkg/crisp/lib/schunck.gi",
+ "pkg/crisp/lib/form.gi",
+ "pkg/crisp/lib/projector.gi",
+ "pkg/crisp/lib/injector.gi",
+ "pkg/crisp/lib/normpro.gi",
+ "pkg/crisp/lib/solveeq.gi",
+ "pkg/crisp/lib/compl.gi",
+ "pkg/crisp/lib/radical.gi",
+ "pkg/crisp/lib/residual.gi",
+ "pkg/crisp/lib/util.gi",
+ "pkg/crisp/lib/samples.gi",
+ "pkg/crisp/lib/socle.gi",
+ "pkg/factint/init.g",
+ "pkg/factint/lib/factint.gd",
+ "pkg/factint/read.g",
+ "pkg/factint/tables/3k2k.g",
+ "pkg/factint/tables/akbk.g",
+ "pkg/factint/tables/factorial.g",
+ "pkg/factint/tables/fibo.g",
+ "pkg/factint/tables/primorial.g",
+ "pkg/factint/lib/general.gi",
+ "pkg/factint/lib/pminus1.gi",
+ "pkg/factint/lib/pplus1.gi",
+ "pkg/factint/lib/ecm.gi",
+ "pkg/factint/lib/cfrac.gi",
+ "pkg/factint/lib/mpqs.gi",
+ "pkg/forms/init.g",
+ "pkg/forms/lib/forms.gd",
+ "pkg/forms/lib/recognition.gd",
+ "pkg/forms/lib/conformal.gd",
+ "pkg/forms/read.g",
+ "pkg/forms/lib/forms.gi",
+ "pkg/forms/lib/recognition.gi",
+ "pkg/forms/lib/classic.gi",
+ "pkg/forms/lib/recognition_new.gi",
+ "pkg/forms/lib/conformal.gi",
+ "pkg/orb/init.g",
+ "pkg/orb/gap/homwdata.gd",
+ "pkg/orb/gap/avltree.gd",
+ "pkg/orb/gap/hash.gd",
+ "pkg/orb/gap/cache.gd",
+ "pkg/orb/gap/orbits.gd",
+ "pkg/orb/gap/search.gd",
+ "pkg/orb/gap/bysuborbit.gd",
+ "pkg/orb/read.g",
+ "pkg/orb/gap/homwdata.gi",
+ "pkg/orb/gap/avltree.gi",
+ "pkg/orb/gap/hash.gi",
+ "pkg/orb/gap/cache.gi",
+ "pkg/orb/gap/orbits.gi",
+ "pkg/orb/gap/search.gi",
+ "pkg/orb/gap/bysuborbit.gi",
+ "pkg/utils/init.g",
+ "pkg/utils/lib/start.gd",
+ "pkg/utils/lib/files.gd",
+ "pkg/utils/lib/groups.gd",
+ "pkg/utils/lib/iterator.gd",
+ "pkg/utils/lib/latex.gd",
+ "pkg/utils/lib/lcset.gd",
+ "pkg/utils/lib/lists.gd",
+ "pkg/utils/lib/magma.gd",
+ "pkg/utils/lib/maps.gd",
+ "pkg/utils/lib/matrix.gd",
+ "pkg/utils/lib/number.gd",
+ "pkg/utils/lib/print.gd",
+ "pkg/utils/lib/record.gd",
+ "pkg/utils/lib/string.gd",
+ "pkg/utils/lib/gslp.gd",
+ "pkg/utils/lib/download.gd",
+ "pkg/utils/read.g",
+ "pkg/utils/lib/files.gi",
+ "pkg/utils/lib/groups.gi",
+ "pkg/utils/lib/iterator.gi",
+ "pkg/utils/lib/latex.gi",
+ "pkg/utils/lib/lcset.gi",
+ "pkg/utils/lib/lists.gi",
+ "pkg/utils/lib/magma.gi",
+ "pkg/utils/lib/maps.gi",
+ "pkg/utils/lib/matrix.gi",
+ "pkg/utils/lib/number.gi",
+ "pkg/utils/lib/print.gi",
+ "pkg/utils/lib/record.gi",
+ "pkg/utils/lib/string.gi",
+ "pkg/utils/lib/gslp.gi",
+ "pkg/utils/lib/download.gi",
+ "pkg/genss/init.g",
+ "pkg/genss/gap/genss.gd",
+ "pkg/genss/gap/setwise.gd",
+ "pkg/genss/read.g",
+ "pkg/genss/gap/genss.gi",
+ "pkg/genss/gap/setwise.gi",
+ "pkg/atlasrep/init.g",
+ "pkg/atlasrep/gap/userpref.g",
+ "pkg/atlasrep/gap/bbox.gd",
+ "pkg/atlasrep/gap/access.gd",
+ "pkg/atlasrep/gap/scanmtx.gd",
+ "pkg/atlasrep/gap/scanmtx.gi",
+ "pkg/atlasrep/gap/types.gd",
+ "pkg/atlasrep/gap/interfac.gd",
+ "pkg/atlasrep/gap/mindeg.gd",
+ "pkg/atlasrep/gap/utils.gd",
+ "pkg/ctbllib/init.g",
+ "pkg/ctbllib/gap4/ctadmin.gd",
+ "pkg/ctbllib/gap4/construc.gd",
+ "pkg/ctbllib/gap4/ctblothe.gd",
+ "pkg/ctbllib/dlnames/dlnames.gd",
+ "pkg/ctbllib/gap4/obsolete.gd",
+ "pkg/ctbllib/gap4/brdbattrX.gd",
+ "pkg/ctbllib/gap4/brdbattrX.gi",
+ "pkg/recog/init.g",
+ "pkg/recog/gap/base/hack.g",
+ "pkg/recog/gap/base/methods.gd",
+ "pkg/recog/gap/base/methsel.gd",
+ "pkg/recog/gap/base/recognition.gd",
+ "pkg/recog/gap/base/kernel.gd",
+ "pkg/recog/gap/base/projective.gd",
+ "pkg/recog/gap/matrix/ppd.gd",
+ "pkg/recog/gap/matrix/classical.gd",
+ "pkg/recog/gap/projective/almostsimple.gd",
+ "pkg/recog/gap/projective/findnormal.gd",
+ "pkg/recog/gap/projective/AnSnOnFDPM.gd",
+ "pkg/spinsym/init.g",
+ "pkg/spinsym/gap/mtx.gd",
+ "pkg/spinsym/gap/fus.gd",
+ "pkg/spinsym/gap/young.gd",
+ "pkg/standardff/init.g",
+ "pkg/standardff/lib/Util.gd",
+ "pkg/standardff/lib/IsIrred.gd",
+ "pkg/standardff/lib/StandardFF.gd",
+ "pkg/standardff/lib/StandardCyc.gd",
+ "pkg/tomlib/init.g",
+ "pkg/tomlib/gap/tmadmin.tmd",
+ "pkg/tomlib/gap/stdgen.gd",
+ "pkg/atlasrep/read.g",
+ "pkg/atlasrep/gap/bbox.gi",
+ "pkg/atlasrep/gap/access.gi",
+ "pkg/atlasrep/gap/types.gi",
+ "pkg/atlasrep/gap/interfac.gi",
+ "pkg/atlasrep/gap/mindeg.gi",
+ "pkg/atlasrep/gap/utlmrkup.g",
+ "pkg/atlasrep/gap/utils.gi",
+ "pkg/atlasrep/gap/test.g",
+ "pkg/atlasrep/gap/json.g",
+ "pkg/atlasrep/gap/obsolete.gd",
+ "pkg/atlasrep/gap/obsolete.gi",
+ "pkg/ctbllib/read.g",
+ "pkg/ctbllib/gap4/ctadmin.gi",
+ "pkg/ctbllib/gap4/ctprimar.g",
+ "pkg/ctbllib/data/firstnames.json",
+ "pkg/ctbllib/data/othernames.json",
+ "pkg/ctbllib/data/fusionsources.json",
+ "pkg/ctbllib/data/extinfo.json",
+ "pkg/ctbllib/data/ctgeneri.tbl",
+ "pkg/ctbllib/data/version",
+ "pkg/ctbllib/data/namerepl.json",
+ "pkg/ctbllib/gap4/construc.gi",
+ "pkg/ctbllib/gap4/ctblothe.gi",
+ "pkg/ctbllib/gap4/test.g",
+ "pkg/ctbllib/dlnames/dlnames.gi",
+ "pkg/ctbllib/gap4/ctbltoct.g",
+ "pkg/ctbllib/gap4/ctdbattr.g",
+ "pkg/ctbllib/gap4/od.g",
+ "pkg/ctbllib/data/odresults.json",
+ "pkg/ctbllib/gap4/atlasstr.g",
+ "pkg/ctbllib/gap4/atlasirr.g",
+ "pkg/recog/read.g",
+ "pkg/recog/gap/base/methods.gi",
+ "pkg/recog/gap/base/methsel.gi",
+ "pkg/recog/gap/base/recognition.gi",
+ "pkg/recog/gap/base/kernel.gi",
+ "pkg/recog/gap/base/projective.gi",
+ "pkg/recog/gap/utils.gi",
+ "pkg/recog/gap/generic/TrivialGroup.gi",
+ "pkg/recog/gap/generic/FewGensAbelian.gi",
+ "pkg/recog/gap/generic/KnownNilpotent.gi",
+ "pkg/recog/gap/perm/giant.gi",
+ "pkg/recog/gap/perm/largebase.gi",
+ "pkg/recog/gap/SnAnBB.gi",
+ "pkg/recog/gap/generic/SnAnUnknownDegree.gi",
+ "pkg/recog/gap/matrix/matimpr.gi",
+ "pkg/recog/gap/matrix/blocks.gi",
+ "pkg/recog/gap/matrix/ppd.gi",
+ "pkg/recog/gap/matrix/classical.gi",
+ "pkg/recog/gap/matrix/slconstr.gi",
+ "pkg/recog/gap/projective/findnormal.gi",
+ "pkg/recog/gap/projective/c6.gi",
+ "pkg/recog/gap/projective/tensor.gi",
+ "pkg/recog/gap/projective/c3c5.gi",
+ "pkg/recog/gap/projective/d247.gi",
+ "pkg/recog/gap/projective/almostsimple/threeelorders.gi",
+ "pkg/recog/gap/projective/almostsimple.gi",
+ "pkg/recog/gap/projective/almostsimple/lietype.gi",
+ "pkg/recog/gap/projective/almostsimple/hints.gi",
+ "pkg/recog/gap/projective/classicalnatural.gi",
+ "pkg/recog/gap/projective/sl2_natural.gi",
+ "pkg/recog/gap/projective/sl.gi",
+ "pkg/recog/gap/projective/AnSnOnFDPM.gi",
+ "pkg/recog/gap/perm.gi",
+ "pkg/recog/gap/matrix.gi",
+ "pkg/recog/gap/projective.gi",
+ "pkg/spinsym/read.g",
+ "pkg/spinsym/gap/mtx.gi",
+ "pkg/spinsym/gap/fus.gi",
+ "pkg/spinsym/gap/young.gi",
+ "pkg/standardff/read.g",
+ "pkg/standardff/lib/Util.gi",
+ "pkg/standardff/lib/IsIrred.gi",
+ "pkg/standardff/lib/StandardFF.gi",
+ "pkg/standardff/lib/StandardCyc.gi",
+ "pkg/standardff/lib/CANFACT.g",
+ "pkg/standardff/lib/TestFuncs.g",
+ "pkg/tomlib/read.g",
+ "pkg/tomlib/gap/tmstdrd.tom",
+ "pkg/tomlib/gap/tmadmin.tmi",
+ "pkg/tomlib/gap/stdgen.gi",
+ "pkg/atlasrep/gap/ctbllib_only.g",
+ "pkg/ctbllib/gap4/atlasrep_only.g",
+ "pkg/ctbllib/gap4/tomlib_only.g",
+ "pkg/ctbllib/data/tom_tbl.json",
+ "pkg/ctbllib/gap4/spinsym_only.g",
+ "pkg/ctbllib/data/grp_atlas.json",
+ "pkg/ctbllib/data/attr_nccl.json",
+ "pkg/ctbllib/data/grp_small.json",
+ "pkg/ctbllib/data/grp_tom.json",
+ "pkg/ctbllib/data/grp_trans.json",
+ "pkg/ctbllib/data/grp_prim.json",
+ "pkg/ctbllib/data/grp_perf.json",
+ "pkg/fga/init.g",
+ "pkg/fga/lib/util.gd",
+ "pkg/fga/lib/Iterated.gd",
+ "pkg/fga/lib/Autom.gd",
+ "pkg/fga/lib/FreeGrps.gd",
+ "pkg/fga/lib/ReprAct.gd",
+ "pkg/fga/lib/Normal.gd",
+ "pkg/fga/lib/ExtAutom.gd",
+ "pkg/fga/lib/Hom.gd",
+ "pkg/fga/lib/AutGrp.gd",
+ "pkg/fga/lib/Intsect.gd",
+ "pkg/fga/lib/Whitehd.gd",
+ "pkg/fga/read.g",
+ "pkg/fga/lib/util.gi",
+ "pkg/fga/lib/Iterated.gi",
+ "pkg/fga/lib/Autom.gi",
+ "pkg/fga/lib/FreeGrps.gi",
+ "pkg/fga/lib/ReprAct.gi",
+ "pkg/fga/lib/Normal.gi",
+ "pkg/fga/lib/Central.gi",
+ "pkg/fga/lib/Index.gi",
+ "pkg/fga/lib/ExtAutom.gi",
+ "pkg/fga/lib/Hom.gi",
+ "pkg/fga/lib/AutGrp.gi",
+ "pkg/fga/lib/Intsect.gi",
+ "pkg/fga/lib/ReprActT.gi",
+ "pkg/fga/lib/Whitehd.gi",
+ "pkg/irredsol/init.g",
+ "pkg/irredsol/lib/util.g",
+ "pkg/irredsol/lib/util.gd",
+ "pkg/irredsol/lib/matmeths.gd",
+ "pkg/irredsol/lib/loading.gd",
+ "pkg/irredsol/lib/loadfp.gd",
+ "pkg/irredsol/lib/access.gd",
+ "pkg/irredsol/lib/iterators.gd",
+ "pkg/irredsol/lib/recognize.gd",
+ "pkg/irredsol/lib/primitive.gd",
+ "pkg/irredsol/lib/recognizeprim.gd",
+ "pkg/irredsol/lib/obsolete.gd",
+ "pkg/irredsol/read.g",
+ "pkg/irredsol/lib/matmeths.gi",
+ "pkg/irredsol/lib/loading.gi",
+ "pkg/irredsol/lib/loadfp.gi",
+ "pkg/irredsol/lib/access.gi",
+ "pkg/irredsol/lib/iterators.gi",
+ "pkg/irredsol/lib/recognize.gi",
+ "pkg/irredsol/lib/primitive.gi",
+ "pkg/irredsol/lib/recognizeprim.gi",
+ "pkg/irredsol/lib/util.gi",
+ "pkg/irredsol/lib/obsolete.gi",
+ "pkg/sophus/init.g",
+ "pkg/sophus/gap/sophus.gd",
+ "pkg/sophus/read.g",
+ "pkg/sophus/gap/general.gi",
+ "pkg/sophus/gap/lienp.gi",
+ "pkg/sophus/gap/liesct.gi",
+ "pkg/sophus/gap/liecover.gi",
+ "pkg/sophus/gap/nicestab.gi",
+ "pkg/sophus/gap/lieautoops.gi",
+ "pkg/sophus/gap/initauts.gi",
+ "pkg/sophus/gap/lieautgrp.gi",
+ "pkg/sophus/gap/allowable.gi",
+ "pkg/sophus/gap/descendant.gi",
+ "pkg/sophus/gap/lieisom.gi",
+ "pkg/sophus/gap/io.gi",
+ "pkg/laguna/init.g",
+ "pkg/laguna/lib/laguna.gd",
+ "pkg/laguna/lib/laguna.g",
+ "pkg/laguna/read.g",
+ "pkg/laguna/lib/laguna.gi",
+ "pkg/autodoc/init.g",
+ "pkg/autodoc/gap/DocumentationTree.gd",
+ "pkg/autodoc/gap/Parser.gd",
+ "pkg/autodoc/gap/AutoDocMainFunction.gd",
+ "pkg/autodoc/gap/ToolFunctions.gd",
+ "pkg/autodoc/gap/Magic.gd",
+ "pkg/autodoc/gap/Markdown.gd",
+ "pkg/autodoc/read.g",
+ "pkg/autodoc/gap/ToolFunctions.gi",
+ "pkg/autodoc/gap/DocumentationTree.gi",
+ "pkg/autodoc/gap/Parser.gi",
+ "pkg/autodoc/gap/AutoDocMainFunction.gi",
+ "pkg/autodoc/gap/Magic.gi",
+ "pkg/autodoc/gap/Markdown.gi",
+ "pkg/packagemanager/init.g",
+ "pkg/packagemanager/gap/PackageManager.gd",
+ "pkg/packagemanager/gap/archive.gd",
+ "pkg/packagemanager/gap/compile.gd",
+ "pkg/packagemanager/gap/directories.gd",
+ "pkg/packagemanager/gap/distro.gd",
+ "pkg/packagemanager/gap/doc.gd",
+ "pkg/packagemanager/gap/download.gd",
+ "pkg/packagemanager/gap/git.gd",
+ "pkg/packagemanager/gap/hg.gd",
+ "pkg/packagemanager/gap/interactive.gd",
+ "pkg/packagemanager/gap/packageinfo.gd",
+ "pkg/packagemanager/read.g",
+ "pkg/packagemanager/gap/PackageManager.gi",
+ "pkg/packagemanager/gap/archive.gi",
+ "pkg/packagemanager/gap/compile.gi",
+ "pkg/packagemanager/gap/directories.gi",
+ "pkg/packagemanager/gap/distro.gi",
+ "pkg/packagemanager/gap/doc.gi",
+ "pkg/packagemanager/gap/download.gi",
+ "pkg/packagemanager/gap/git.gi",
+ "pkg/packagemanager/gap/hg.gi",
+ "pkg/packagemanager/gap/interactive.gi",
+ "pkg/packagemanager/gap/packageinfo.gi",
+ "pkg/radiroot/init.g",
+ "pkg/radiroot/lib/Radicals.gd",
+ "pkg/radiroot/lib/SplittField.gd",
+ "pkg/radiroot/lib/Manipulations.gd",
+ "pkg/radiroot/lib/Strings.gd",
+ "pkg/radiroot/lib/Maple.gd",
+ "pkg/radiroot/read.g",
+ "pkg/radiroot/lib/Radicals.gi",
+ "pkg/radiroot/lib/SplittField.gi",
+ "pkg/radiroot/lib/Manipulations.gi",
+ "pkg/radiroot/lib/Strings.gi",
+ "pkg/radiroot/lib/Maple.gi",
+ "pkg/aclib/init.g",
+ "pkg/aclib/gap/groups.gd",
+ "pkg/cryst/init.g",
+ "pkg/cryst/gap/common.gd",
+ "pkg/cryst/gap/cryst.gd",
+ "pkg/cryst/gap/hom.gd",
+ "pkg/cryst/gap/wyckoff.gd",
+ "pkg/cryst/gap/zass.gd",
+ "pkg/cryst/gap/max.gd",
+ "pkg/cryst/gap/color.gd",
+ "pkg/cryst/gap/equiv.gd",
+ "pkg/cryst/grp/spacegrp.gd",
+ "pkg/crystcat/init.g",
+ "pkg/crystcat/lib/crystcat.gd",
+ "pkg/polenta/init.g",
+ "pkg/polenta/lib/finite.gd",
+ "pkg/polenta/lib/info.gd",
+ "pkg/polenta/lib/basic.gd",
+ "pkg/polenta/exam/test.gd",
+ "pkg/polenta/lib/cpcs.gd",
+ "pkg/polenta/lib/present.gd",
+ "pkg/polenta/lib/solvable.gd",
+ "pkg/polenta/lib/series.gd",
+ "pkg/polenta/lib/subgroups.gd",
+ "pkg/polenta/lib/ispolyz.gd",
+ "pkg/aclib/read.g",
+ "pkg/aclib/gap/matgrp3.gi",
+ "pkg/aclib/gap/matgrp4.gi",
+ "pkg/aclib/gap/matgrp.gi",
+ "pkg/aclib/gap/pcpgrp3.gi",
+ "pkg/aclib/gap/pcpgrp4.gi",
+ "pkg/aclib/gap/pcpgrp.gi",
+ "pkg/aclib/gap/betti.gi",
+ "pkg/aclib/gap/union.gi",
+ "pkg/aclib/gap/extend.gi",
+ "pkg/aclib/gap/crystgrp.gi",
+ "pkg/cryst/read.g",
+ "pkg/cryst/gap/common.gi",
+ "pkg/cryst/gap/hom.gi",
+ "pkg/cryst/gap/cryst.gi",
+ "pkg/cryst/gap/cryst2.gi",
+ "pkg/cryst/gap/fpgrp.gi",
+ "pkg/cryst/gap/zass.gi",
+ "pkg/cryst/gap/max.gi",
+ "pkg/cryst/gap/wyckoff.gi",
+ "pkg/cryst/gap/color.gi",
+ "pkg/cryst/gap/noxgap.gi",
+ "pkg/cryst/gap/pcpgrp.gi",
+ "pkg/cryst/gap/orbstab.gi",
+ "pkg/cryst/gap/equiv.gi",
+ "pkg/cryst/grp/spacegrp.grp",
+ "pkg/cryst/grp/spacegrp.gi",
+ "pkg/crystcat/read.g",
+ "pkg/crystcat/grp/crystcat.grp",
+ "pkg/crystcat/lib/crystcat.gi",
+ "pkg/crystcat/lib/normalizer.gi",
+ "pkg/polenta/read.g",
+ "pkg/polenta/lib/finite.gi",
+ "pkg/polenta/lib/basic.gi",
+ "pkg/polenta/lib/unipo.gi",
+ "pkg/polenta/lib/series.gi",
+ "pkg/polenta/lib/semi.gi",
+ "pkg/polenta/lib/ispoly.gi",
+ "pkg/polenta/lib/cpcs.gi",
+ "pkg/polenta/lib/present.gi",
+ "pkg/polenta/lib/isom.gi",
+ "pkg/polenta/lib/solvable.gi",
+ "pkg/polenta/exam/exam.gi",
+ "pkg/polenta/exam/test.gi",
+ "pkg/polenta/lib/subgroups.gi",
+ "pkg/polenta/lib/ispolyz.gi",
+ "pkg/resclasses/init.g",
+ "pkg/resclasses/lib/general.gd",
+ "pkg/resclasses/lib/z_pi.gd",
+ "pkg/resclasses/lib/resclass.gd",
+ "pkg/resclasses/lib/fixedrep.gd",
+ "pkg/resclasses/read.g",
+ "pkg/resclasses/lib/general.gi",
+ "pkg/resclasses/lib/resclaux.g",
+ "pkg/resclasses/lib/z_pi.gi",
+ "pkg/resclasses/lib/resclass.gi",
+ "pkg/resclasses/lib/fixedrep.gi",
+ "lib/obsolete.gi",
+ "pkg/4ti2interface/doc/manual.six",
+ "pkg/ace/doc/manual.six",
+ "pkg/aclib/doc/manual.six",
+ "pkg/agt/doc/manual.six",
+ "pkg/alco/doc/manual.six",
+ "pkg/alnuth/doc/manual.six",
+ "pkg/anupq/doc/manual.six",
+ "pkg/atlasrep/doc/manual.six",
+ "pkg/autodoc/doc/manual.six",
+ "pkg/automata/doc/manual.six",
+ "pkg/automgrp/doc/manual.six",
+ "pkg/autpgrp/doc/manual.six",
+ "pkg/browse/doc/manual.six",
+ "pkg/cap/doc/manual.six",
+ "pkg/caratinterface/doc/manual.six",
+ "pkg/cddinterface/doc/manual.six",
+ "pkg/circle/doc/manual.six",
+ "pkg/classicalmaximals/doc/manual.six",
+ "pkg/classicpres/doc/manual.six",
+ "pkg/cohomolo/doc/manual.six",
+ "pkg/congruence/doc/manual.six",
+ "pkg/corefreesub/doc/manual.six",
+ "pkg/corelg/doc/manual.six",
+ "pkg/crime/doc/manual.six",
+ "pkg/crisp/doc/manual.six",
+ "pkg/crypting/doc/manual.six",
+ "pkg/cryst/doc/manual.six",
+ "pkg/crystcat/doc/manual.six",
+ "pkg/ctbllib/doc/manual.six",
+ "pkg/ctbllib/doc2/manual.six",
+ "pkg/cubefree/doc/manual.six",
+ "pkg/curlinterface/doc/manual.six",
+ "pkg/cvec/doc/manual.six",
+ "pkg/datastructures/doc/manual.six",
+ "pkg/deepthought/doc/manual.six",
+ "pkg/design/doc/manual.six",
+ "pkg/difsets/doc/manual.six",
+ "pkg/digraphs/doc/manual.six",
+ "pkg/edim/doc/manual.six",
+ "pkg/example/doc/manual.six",
+ "pkg/examplesforhomalg/doc/manual.six",
+ "pkg/factint/doc/manual.six",
+ "pkg/ferret/doc/manual.six",
+ "pkg/fga/doc/manual.six",
+ "pkg/fining/doc/manual.six",
+ "pkg/float/doc/manual.six",
+ "pkg/format/doc/manual.six",
+ "pkg/forms/doc/manual.six",
+ "pkg/fplsa/doc/manual.six",
+ "pkg/fr/doc/manual.six",
+ "pkg/francy/doc/manual.six",
+ "pkg/fwtree/doc/manual.six",
+ "pkg/gapdoc/doc/manual.six",
+ "pkg/gapdoc/example/manual.six",
+ "pkg/gauss/doc/manual.six",
+ "pkg/gaussforhomalg/doc/manual.six",
+ "pkg/gbnp/doc/manual.six",
+ "pkg/generalizedmorphismsforcap/doc/manual.six",
+ "pkg/genss/doc/manual.six",
+ "pkg/gradedmodules/doc/manual.six",
+ "pkg/gradedringforhomalg/doc/manual.six",
+ "pkg/grape/doc/manual.six",
+ "pkg/groupoids/doc/manual.six",
+ "pkg/grpconst/doc/manual.six",
+ "pkg/guarana/doc/manual.six",
+ "pkg/guava/doc/manual.six",
+ "pkg/hap/doc/manual.six",
+ "pkg/hapcryst/doc/manual.six",
+ "pkg/hecke/doc/manual.six",
+ "pkg/help/doc/manual.six",
+ "pkg/homalg/doc/manual.six",
+ "pkg/homalgtocas/doc/manual.six",
+ "pkg/ibnp/doc/manual.six",
+ "pkg/idrel/doc/manual.six",
+ "pkg/images/doc/manual.six",
+ "pkg/inducereduce/doc/manual.six",
+ "pkg/intpic/doc/manual.six",
+ "pkg/io/doc/manual.six",
+ "pkg/io_forhomalg/doc/manual.six",
+ "pkg/irredsol/doc/manual.six",
+ "pkg/itc/doc/manual.six",
+ "pkg/json/doc/manual.six",
+ "pkg/jupyterkernel/doc/manual.six",
+ "pkg/jupyterviz/doc/manual.six",
+ "pkg/kan/doc/manual.six",
+ "pkg/kbmag/doc/manual.six",
+ "pkg/laguna/doc/manual.six",
+ "pkg/liealgdb/doc/manual.six",
+ "pkg/liepring/doc/manual.six",
+ "pkg/liering/doc/manual.six",
+ "pkg/linearalgebraforcap/doc/manual.six",
+ "pkg/lins/doc/manual.six",
+ "pkg/localizeringforhomalg/doc/manual.six",
+ "pkg/localnr/doc/manual.six",
+ "pkg/loops/doc/manual.six",
+ "pkg/lpres/doc/manual.six",
+ "pkg/majoranaalgebras/doc/manual.six",
+ "pkg/mapclass/doc/manual.six",
+ "pkg/matgrp/doc/manual.six",
+ "pkg/matricesforhomalg/doc/manual.six",
+ "pkg/modisom/doc/manual.six",
+ "pkg/modulargroup/doc/manual.six",
+ "pkg/modulepresentationsforcap/doc/manual.six",
+ "pkg/modules/doc/manual.six",
+ "pkg/monoidalcategories/doc/manual.six",
+ "pkg/nconvex/doc/manual.six",
+ "pkg/nilmat/doc/manual.six",
+ "pkg/nock/doc/manual.six",
+ "pkg/nofoma/doc/manual.six",
+ "pkg/normalizinterface/doc/manual.six",
+ "pkg/nq/doc/manual.six",
+ "pkg/numericalsgps/doc/manual.six",
+ "pkg/openmath/doc/manual.six",
+ "pkg/orb/doc/manual.six",
+ "pkg/origami/doc/manual.six",
+ "pkg/packagemaker/doc/manual.six",
+ "pkg/packagemanager/doc/manual.six",
+ "pkg/patternclass/doc/manual.six",
+ "pkg/permut/doc/manual.six",
+ "pkg/polenta/doc/manual.six",
+ "pkg/polycyclic/doc/manual.six",
+ "pkg/polymaking/doc/manual.six",
+ "pkg/primgrp/doc/manual.six",
+ "pkg/profiling/doc/manual.six",
+ "pkg/qdistrnd/doc/manual.six",
+ "pkg/qpa/doc/manual.six",
+ "pkg/quagroup/doc/manual.six",
+ "pkg/radiroot/doc/manual.six",
+ "pkg/rcwa/doc/manual.six",
+ "pkg/rds/doc/manual.six",
+ "pkg/recog/doc/manual.six",
+ "pkg/repndecomp/doc/manual.six",
+ "pkg/repsn/doc/manual.six",
+ "pkg/resclasses/doc/manual.six",
+ "pkg/ringsforhomalg/doc/manual.six",
+ "pkg/sco/doc/manual.six",
+ "pkg/scscp/doc/manual.six",
+ "pkg/semigroups/doc/manual.six",
+ "pkg/sglppow/doc/manual.six",
+ "pkg/sgpviz/doc/manual.six",
+ "pkg/simpcomp/doc/manual.six",
+ "pkg/singular/doc/manual.six",
+ "pkg/sl2reps/doc/manual.six",
+ "pkg/sla/doc/manual.six",
+ "pkg/smallantimagmas/doc/manual.six",
+ "pkg/smallclassnr/doc/manual.six",
+ "pkg/smallgrp/doc/manual.six",
+ "pkg/smallsemi/doc/manual.six",
+ "pkg/sonata/doc/ref/manual.six",
+ "pkg/sonata/doc/tut/manual.six",
+ "pkg/sophus/doc/manual.six",
+ "pkg/sotgrps/doc/manual.six",
+ "pkg/spinsym/doc/manual.six",
+ "pkg/standardff/doc/manual.six",
+ "pkg/symbcompcc/doc/manual.six",
+ "pkg/thelma/doc/manual.six",
+ "pkg/tomlib/doc/manual.six",
+ "pkg/toolsforhomalg/doc/manual.six",
+ "pkg/toric/doc/manual.six",
+ "pkg/transgrp/doc/manual.six",
+ "pkg/twistedconjugacy/doc/manual.six",
+ "pkg/typeset/doc/manual.six",
+ "pkg/ugaly/doc/manual.six",
+ "pkg/unipot/doc/manual.six",
+ "pkg/unitlib/doc/manual.six",
+ "pkg/utils/doc/manual.six",
+ "pkg/uuid/doc/manual.six",
+ "pkg/walrus/doc/manual.six",
+ "pkg/wedderga/doc/manual.six",
+ "pkg/wpe/doc/manual.six",
+ "pkg/xgap/doc/manual.six",
+ "pkg/xmod/doc/manual.six",
+ "pkg/xmodalg/doc/manual.six",
+ "pkg/yangbaxter/doc/manual.six",
+ "pkg/zeromqinterface/doc/manual.six"
+]
diff --git a/etc/emscripten/web-template/gap-fs.js b/etc/emscripten/web-template/gap-fs.js
index f3a1467d42..ca8ea4f23d 100644
--- a/etc/emscripten/web-template/gap-fs.js
+++ b/etc/emscripten/web-template/gap-fs.js
@@ -1,3 +1,29 @@
+// Instrument fetch and XMLHttpRequest so the page can collect the list of
+// URLs the worker actually requests, for rebuilding startup_manifest.json
+// without scraping the browser network panel. Each unique URL is posted
+// to the main thread as { type: "gap-fetched", url: ... }.
+(function instrumentFetches() {
+ const seen = new Set();
+ const report = (raw) => {
+ if (typeof raw !== "string") return;
+ if (seen.has(raw)) return;
+ seen.add(raw);
+ self.postMessage({ type: "gap-fetched", url: raw });
+ };
+
+ const origFetch = self.fetch;
+ self.fetch = function(input, init) {
+ report(typeof input === "string" ? input : input && input.url);
+ return origFetch.apply(this, arguments);
+ };
+
+ const origOpen = XMLHttpRequest.prototype.open;
+ XMLHttpRequest.prototype.open = function(method, url) {
+ report(url);
+ return origOpen.apply(this, arguments);
+ };
+})();
+
self.Module = self.Module || {};
self.Module.preRun = self.Module.preRun || [];
@@ -43,8 +69,12 @@ self.Module.preRun.push(function() {
if (p.startsWith('/')) p = p.substring(1);
startupSet.add(p);
});
+ } else {
+ console.info("startup_manifest.json not present; falling back to fully lazy loading");
}
- } catch (e) {}
+ } catch (e) {
+ console.warn("Failed to load startup_manifest.json:", e);
+ }
var fetchPromises = fileList.map(async function(appPath) {
var fetchRelativePath = appPath.split('/').map(encodeURIComponent).join('/');
@@ -58,16 +88,15 @@ self.Module.preRun.push(function() {
FS.stat(idbfsPath);
FS.writeFile(finalAppPath, FS.readFile(idbfsPath));
} catch (e) {
- try {
- const response = await fetch(fetchPath);
- if (response.ok) {
- const buffer = await response.arrayBuffer();
- const data = new Uint8Array(buffer);
- FS.writeFile(finalAppPath, data);
- FS.writeFile(idbfsPath, data);
- needsSave = true;
- }
- } catch (fetchErr) {}
+ const response = await fetch(fetchPath);
+ if (!response.ok) {
+ throw new Error("Failed to fetch startup file " + fetchPath + ": " + response.status);
+ }
+ const buffer = await response.arrayBuffer();
+ const data = new Uint8Array(buffer);
+ FS.writeFile(finalAppPath, data);
+ FS.writeFile(idbfsPath, data);
+ needsSave = true;
}
} else {
var parts = appPath.split('/');
diff --git a/etc/emscripten/web-template/index.html b/etc/emscripten/web-template/index.html
index b51df45fb8..d5f1bec759 100755
--- a/etc/emscripten/web-template/index.html
+++ b/etc/emscripten/web-template/index.html
@@ -1,22 +1,185 @@
-
+
+
- gap-wasm
+
+
+ GAP in the browser
+
-
+
+
GAP in the browser
+
+ A WebAssembly build of GAP
+ running entirely in your browser — useful for trying things out
+ without installing. Not all packages work, working memory is
+ capped, and performance is reduced compared to a native build.
+ For real work, install GAP from
+ www.gap-system.org.
+
+
+
+
+ What is this? · Licensing
+
+ GAP is a system for
+ computational discrete algebra, with particular emphasis on
+ computational group theory. This page is a self-contained
+ WebAssembly build, served as a static site and run inside a
+ Web Worker; you interact with it through an
+ xterm-pty
+ terminal in the page below.
+
+
+ To get started, try 1+1;,
+ Factorial(20);, or SymmetricGroup(5);.
+ The full GAP
+ manuals apply, with two caveats: some packages won't load
+ (anything that needs a native compiler or system library), and
+ anything that wants the local filesystem won't work.
+
+
+ Files downloaded on first visit are cached in your browser's
+ IndexedDB, so subsequent visits start much faster. Clear the
+ site data to reset the cache.
+
+ Loading GAP… The first visit downloads several tens of megabytes;
+ subsequent visits are cached in your browser and load much faster.
+
+
+
+ This page needs SharedArrayBuffer, which is only
+ available when the page is served with the headers
+ Cross-Origin-Opener-Policy: same-origin and
+ Cross-Origin-Embedder-Policy: require-corp. The
+ bundled service worker handles this on hosts where you can't set
+ headers (e.g. GitHub Pages); for local hosting use
+ etc/emscripten/serve.py.
+
+
+
+
+
+
+
+
diff --git a/grp/glzmodmz.gi b/grp/glzmodmz.gi
index 9271ea6976..97d5e7ca77 100644
--- a/grp/glzmodmz.gi
+++ b/grp/glzmodmz.gi
@@ -379,7 +379,7 @@ local oper,n,R,o,nrit,
if fp <>fail then
# extend presentation
bas:=Basis(sub,bas);
- RUN_IN_GGMBI:=true;
+ PushOptions( rec( Run_In_GGMBI:= true ) );
hom:=GroupGeneralMappingByImagesNC(g,fp,gens,GeneratorsOfGroup(fp));
hom:=LiftFactorFpHom(hom,g,SubgroupNC(g,basm),rec(
pcgs:=basm,
@@ -392,7 +392,7 @@ local oper,n,R,o,nrit,
return List(Coefficients(bas,e),Int);
end
));
- RUN_IN_GGMBI:=false;
+ PopOptions();
#simplify Image to avoid explosion of generator number
fp:=Range(hom);
if true then
@@ -412,11 +412,9 @@ local oper,n,R,o,nrit,
k:=TzPreImagesNewGens(e);
k:=List(k,x->j[1][Position(OldGeneratorsOfPresentation(e),x)]);
- RUN_IN_GGMBI:=true;
hom:=GroupHomomorphismByImagesNC(g,fp,
k,
- GeneratorsOfGroup(fp));
- RUN_IN_GGMBI:=false;
+ GeneratorsOfGroup(fp) : Run_In_GGMBI:= true );
fi;
SetIsomorphismFpGroup(g,hom);
diff --git a/grp/perf13.grp b/grp/perf13.grp
index 0f9a715bf9..9a66aacec6 100644
--- a/grp/perf13.grp
+++ b/grp/perf13.grp
@@ -5,7 +5,7 @@
## This data was computed by Alexander Hulpke
## It is distributed under the artistic license 2.0
## https://opensource.org/licenses/Artistic-2.0
-## as well as (dual licensing) under GPL 2
+## as well as (dual licensing) under GPL-2.0-or-later
PERFGRP[96]:=[# 61440.1
[[1,"abcde",
diff --git a/grp/perf14.grp b/grp/perf14.grp
index eccd748827..fe20d8d587 100644
--- a/grp/perf14.grp
+++ b/grp/perf14.grp
@@ -5,7 +5,7 @@
## This data was computed by Alexander Hulpke
## It is distributed under the artistic license 2.0
## https://opensource.org/licenses/Artistic-2.0
-## as well as (dual licensing) under GPL 2
+## as well as (dual licensing) under GPL-2.0-or-later
PERFGRP[111]:=[# 86016.1
[[1,"abcd",
diff --git a/grp/perf15.grp b/grp/perf15.grp
index 3e466c5c5b..96880d1a09 100644
--- a/grp/perf15.grp
+++ b/grp/perf15.grp
@@ -5,7 +5,7 @@
## This data was computed by Alexander Hulpke
## It is distributed under the artistic license 2.0
## https://opensource.org/licenses/Artistic-2.0
-## as well as (dual licensing) under GPL 2
+## as well as (dual licensing) under GPL-2.0-or-later
PERFGRP[131]:=[# 122880.1
[[1,"abcdef",
diff --git a/grp/perf16.grp b/grp/perf16.grp
index 31da9f936f..3d74dd9c6e 100644
--- a/grp/perf16.grp
+++ b/grp/perf16.grp
@@ -5,7 +5,7 @@
## This data was computed by Alexander Hulpke
## It is distributed under the artistic license 2.0
## https://opensource.org/licenses/Artistic-2.0
-## as well as (dual licensing) under GPL 2
+## as well as (dual licensing) under GPL-2.0-or-later
PERFGRP[150]:=[# 172032.1
[[1,"abc",
diff --git a/grp/perf17.grp b/grp/perf17.grp
index dce726788d..9f569b8930 100644
--- a/grp/perf17.grp
+++ b/grp/perf17.grp
@@ -5,7 +5,7 @@
## This data was computed by Alexander Hulpke
## It is distributed under the artistic license 2.0
## https://opensource.org/licenses/Artistic-2.0
-## as well as (dual licensing) under GPL 2
+## as well as (dual licensing) under GPL-2.0-or-later
PERFGRP[179]:=[# 245760.1
[[1,"abcde",
diff --git a/grp/perf18.grp b/grp/perf18.grp
index e142e995b2..66d6548ebd 100644
--- a/grp/perf18.grp
+++ b/grp/perf18.grp
@@ -5,7 +5,7 @@
## This data was computed by Alexander Hulpke
## It is distributed under the artistic license 2.0
## https://opensource.org/licenses/Artistic-2.0
-## as well as (dual licensing) under GPL 2
+## as well as (dual licensing) under GPL-2.0-or-later
PERFGRP[200]:=[# 344064.1
[[1,"abcd",
diff --git a/grp/perf19.grp b/grp/perf19.grp
index abcc2320e7..cbe80ff733 100644
--- a/grp/perf19.grp
+++ b/grp/perf19.grp
@@ -5,7 +5,7 @@
## This data was computed by Alexander Hulpke
## It is distributed under the artistic license 2.0
## https://opensource.org/licenses/Artistic-2.0
-## as well as (dual licensing) under GPL 2
+## as well as (dual licensing) under GPL-2.0-or-later
PERFGRP[210]:=[# 368640.1
[[1,"abcdef",
diff --git a/grp/perf20.grp b/grp/perf20.grp
index d9fec32164..d14b2567e8 100644
--- a/grp/perf20.grp
+++ b/grp/perf20.grp
@@ -5,7 +5,7 @@
## This data was computed by Alexander Hulpke
## It is distributed under the artistic license 2.0
## https://opensource.org/licenses/Artistic-2.0
-## as well as (dual licensing) under GPL 2
+## as well as (dual licensing) under GPL-2.0-or-later
PERFGRP[244]:=[# 491520.1
[[1,"abcde",
diff --git a/grp/perf21.grp b/grp/perf21.grp
index 5488fdc506..0a723692a3 100644
--- a/grp/perf21.grp
+++ b/grp/perf21.grp
@@ -5,7 +5,7 @@
## This data was computed by Alexander Hulpke
## It is distributed under the artistic license 2.0
## https://opensource.org/licenses/Artistic-2.0
-## as well as (dual licensing) under GPL 2
+## as well as (dual licensing) under GPL-2.0-or-later
PERFGRP[276]:=[# 688128.1
[[1,"abcde",
diff --git a/grp/perf22.grp b/grp/perf22.grp
index ab14628e3f..873de9394a 100644
--- a/grp/perf22.grp
+++ b/grp/perf22.grp
@@ -5,7 +5,7 @@
## This data was computed by Alexander Hulpke
## It is distributed under the artistic license 2.0
## https://opensource.org/licenses/Artistic-2.0
-## as well as (dual licensing) under GPL 2
+## as well as (dual licensing) under GPL-2.0-or-later
number:=[ 1, 1, 1, 1, 1, 1, 1, 1, 1, 2, 1, 1, 1, 2, 7, 1, 1, 1, 1, 3, 1, 1,
1, 7, 1, 2, 1, 1, 1, 1, 1, 1, 1, 1, 2, 2, 1, 5, 1, 1, 3, 1, 1, 9, 4, 1, 1,
diff --git a/grp/perf23.grp b/grp/perf23.grp
index b260d3a331..e7cc9f0523 100644
--- a/grp/perf23.grp
+++ b/grp/perf23.grp
@@ -5,7 +5,7 @@
## This data was computed by Alexander Hulpke
## It is distributed under the artistic license 2.0
## https://opensource.org/licenses/Artistic-2.0
-## as well as (dual licensing) under GPL 2
+## as well as (dual licensing) under GPL-2.0-or-later
PERFGRP[330]:=[# 983040.1
[[1,"abcdef",
diff --git a/grp/perf24.grp b/grp/perf24.grp
index 672b2f4d84..b48d5514f9 100644
--- a/grp/perf24.grp
+++ b/grp/perf24.grp
@@ -5,7 +5,7 @@
## This data was computed by Alexander Hulpke
## It is distributed under the artistic license 2.0
## https://opensource.org/licenses/Artistic-2.0
-## as well as (dual licensing) under GPL 2
+## as well as (dual licensing) under GPL-2.0-or-later
PERFGRP[332]:=[# 1008000.1
[[1,"abcdef",
diff --git a/grp/perf25.grp b/grp/perf25.grp
index 1e51e86fc2..a3967e1db6 100644
--- a/grp/perf25.grp
+++ b/grp/perf25.grp
@@ -5,7 +5,7 @@
## This data was computed by Alexander Hulpke
## It is distributed under the artistic license 2.0
## https://opensource.org/licenses/Artistic-2.0
-## as well as (dual licensing) under GPL 2
+## as well as (dual licensing) under GPL-2.0-or-later
PERFGRP[355]:=[# 1180980.1
[[1,"abcde",
diff --git a/grp/perf26.grp b/grp/perf26.grp
index f7486d8e91..7af1e2a545 100644
--- a/grp/perf26.grp
+++ b/grp/perf26.grp
@@ -5,7 +5,7 @@
## This data was computed by Alexander Hulpke
## It is distributed under the artistic license 2.0
## https://opensource.org/licenses/Artistic-2.0
-## as well as (dual licensing) under GPL 2
+## as well as (dual licensing) under GPL-2.0-or-later
PERFGRP[371]:=[# 1290240.1
[[1,"abcdefg",
diff --git a/grp/perf28.grp b/grp/perf28.grp
index 69b0382d26..c9f45efb72 100644
--- a/grp/perf28.grp
+++ b/grp/perf28.grp
@@ -5,7 +5,7 @@
## This data was computed by Alexander Hulpke
## It is distributed under the artistic license 2.0
## https://opensource.org/licenses/Artistic-2.0
-## as well as (dual licensing) under GPL 2
+## as well as (dual licensing) under GPL-2.0-or-later
PERFGRP[382]:=[# 1382400.1
[[1,"abcdefg",
diff --git a/grp/perf29.grp b/grp/perf29.grp
index fcffbacfd0..dcdc30b9e0 100644
--- a/grp/perf29.grp
+++ b/grp/perf29.grp
@@ -5,7 +5,7 @@
## This data was computed by Alexander Hulpke
## It is distributed under the artistic license 2.0
## https://opensource.org/licenses/Artistic-2.0
-## as well as (dual licensing) under GPL 2
+## as well as (dual licensing) under GPL-2.0-or-later
PERFGRP[396]:=[# 1474560.1
[[1,"abcdefg",
diff --git a/grp/perf30.grp b/grp/perf30.grp
index 09144844f8..948a0c1e02 100644
--- a/grp/perf30.grp
+++ b/grp/perf30.grp
@@ -5,7 +5,7 @@
## This data was computed by Alexander Hulpke
## It is distributed under the artistic license 2.0
## https://opensource.org/licenses/Artistic-2.0
-## as well as (dual licensing) under GPL 2
+## as well as (dual licensing) under GPL-2.0-or-later
PERFGRP[421]:=[# 1749600.1
[[1,"abcdefgh",
diff --git a/grp/perf31.grp b/grp/perf31.grp
index ca3418d68a..afc2d69797 100644
--- a/grp/perf31.grp
+++ b/grp/perf31.grp
@@ -5,7 +5,7 @@
## This data was computed by Alexander Hulpke
## It is distributed under the artistic license 2.0
## https://opensource.org/licenses/Artistic-2.0
-## as well as (dual licensing) under GPL 2
+## as well as (dual licensing) under GPL-2.0-or-later
PERFGRP[435]:=[# 1843200.1
[[1,"abcdef",
diff --git a/grp/perf32.grp b/grp/perf32.grp
index a33d812d03..ee0f128a89 100644
--- a/grp/perf32.grp
+++ b/grp/perf32.grp
@@ -5,7 +5,7 @@
## This data was computed by Alexander Hulpke
## It is distributed under the artistic license 2.0
## https://opensource.org/licenses/Artistic-2.0
-## as well as (dual licensing) under GPL 2
+## as well as (dual licensing) under GPL-2.0-or-later
PERFGRP[436]:=[# 1843968.1
[[1,"abcdef",
diff --git a/grp/perf34.grp b/grp/perf34.grp
index e78fe08416..683173f859 100644
--- a/grp/perf34.grp
+++ b/grp/perf34.grp
@@ -5,7 +5,7 @@
## This data was computed by Alexander Hulpke
## It is distributed under the artistic license 2.0
## https://opensource.org/licenses/Artistic-2.0
-## as well as (dual licensing) under GPL 2
+## as well as (dual licensing) under GPL-2.0-or-later
PERFGRP[452]:=[# 1975680.1
[[1,"abcd",
diff --git a/hpcgap/lib/ffeconway.gi b/hpcgap/lib/ffeconway.gi
index ff9d82145e..d148ad64f5 100644
--- a/hpcgap/lib/ffeconway.gi
+++ b/hpcgap/lib/ffeconway.gi
@@ -80,7 +80,7 @@ FFECONWAY.SetUpConwayStuff := function(p,d)
if not IsCheapConwayPolynomial(p,d) then
Error("Conway Polynomial ",p,"^",d,
- " will need to computed and might be slow\n", "return to continue");
+ " will need to be computed and might be slow");
fi;
cp := CoefficientsOfUnivariatePolynomial(ConwayPolynomial(p,d));
diff --git a/lib/algebra.gi b/lib/algebra.gi
index e8457b37e1..df6d32f75f 100644
--- a/lib/algebra.gi
+++ b/lib/algebra.gi
@@ -3647,7 +3647,7 @@ InstallMethod( CentralIdempotentsOfAlgebra,
until k>Length(ideals);
- id:= List( ids, e -> PreImagesRepresentative( hom, e ) );
+ id:= List( ids, e -> PreImagesRepresentativeNC( hom, e ) );
# Now we lift the idempotents to the big algebra `A'. The
# first idempotent is lifted as follows:
diff --git a/lib/algfp.gi b/lib/algfp.gi
index c65a8ec796..51adff0b6d 100644
--- a/lib/algfp.gi
+++ b/lib/algfp.gi
@@ -705,7 +705,7 @@ InstallHandlingByNiceBasis( "IsFpAlgebraElementsSpace", rec(
if hom = fail then
TryNextMethod();
fi;
- return PreImagesRepresentative( hom, r );
+ return PreImagesRepresentativeNC( hom, r );
end ) );
diff --git a/lib/alghom.gi b/lib/alghom.gi
index 8dc79c6efd..b28b163047 100644
--- a/lib/alghom.gi
+++ b/lib/alghom.gi
@@ -576,16 +576,29 @@ InstallMethod( ImagesRepresentative,
#############################################################################
##
+#M PreImagesRepresentativeNC( , ) . . . . . for algebra g.m.b.i.
#M PreImagesRepresentative( , ) . . . . . . for algebra g.m.b.i.
##
+InstallMethod( PreImagesRepresentativeNC,
+ "for algebra g.m.b.i., and element",
+ FamRangeEqFamElm,
+ [ IsGeneralMapping and IsAlgebraGeneralMappingByImagesDefaultRep,
+ IsObject ],
+ function( map, elm )
+ return PreImagesRepresentativeNC(
+ AsLeftModuleGeneralMappingByImages(map), elm );
+ end );
+
InstallMethod( PreImagesRepresentative,
"for algebra g.m.b.i., and element",
FamRangeEqFamElm,
[ IsGeneralMapping and IsAlgebraGeneralMappingByImagesDefaultRep,
IsObject ],
function( map, elm )
- return PreImagesRepresentative( AsLeftModuleGeneralMappingByImages(map),
- elm );
+ if not ( elm in Range( map ) ) then
+ return fail;
+ fi;
+ return PreImagesRepresentativeNC( map, elm );
end );
@@ -902,6 +915,7 @@ InstallMethod( ImagesRepresentative,
#############################################################################
##
+#M PreImagesRepresentativeNC( , )
#M PreImagesRepresentative( , )
##
BindGlobal( "PreImagesRepresentativeOperationAlgebraHomomorphism", function( ophom, mat )
@@ -915,12 +929,22 @@ BindGlobal( "PreImagesRepresentativeOperationAlgebraHomomorphism", function( oph
return mat;
end );
-InstallMethod( PreImagesRepresentative,
+InstallMethod( PreImagesRepresentativeNC,
"for an operation algebra homomorphism, and an element",
FamRangeEqFamElm,
[ IsOperationAlgebraHomomorphismDefaultRep, IsMatrix ],
PreImagesRepresentativeOperationAlgebraHomomorphism );
+InstallMethod( PreImagesRepresentative,
+ "for an operation algebra homomorphism, and an element",
+ FamRangeEqFamElm,
+ [ IsOperationAlgebraHomomorphismDefaultRep, IsMatrix ],
+ function( ophom, mat )
+ if not ( mat in Range( ophom ) ) then
+ return fail;
+ fi;
+ return PreImagesRepresentativeOperationAlgebraHomomorphism( ophom, mat );
+end );
#############################################################################
##
@@ -1076,14 +1100,25 @@ InstallMethod( ImagesRepresentative,
#############################################################################
##
+#M PreImagesRepresentativeNC( , )
#M PreImagesRepresentative( , )
##
-InstallMethod( PreImagesRepresentative,
+InstallMethod( PreImagesRepresentativeNC,
"for an alg. hom. from f. p. algebra, and an element",
FamRangeEqFamElm,
[ IsAlgebraHomomorphismFromFpRep, IsMatrix ],
PreImagesRepresentativeOperationAlgebraHomomorphism );
+InstallMethod( PreImagesRepresentative,
+ "for an alg. hom. from f. p. algebra, and an element",
+ FamRangeEqFamElm,
+ [ IsAlgebraHomomorphismFromFpRep, IsMatrix ],
+ function( ophom, mat );
+ if not ( mat in Range( ophom ) ) then
+ return fail;
+ fi;
+ return PreImagesRepresentativeOperationAlgebraHomomorphism( ophom, mat );
+ end );
#############################################################################
##
diff --git a/lib/alglie.gd b/lib/alglie.gd
index 31cc718ee0..7200f28451 100644
--- a/lib/alglie.gd
+++ b/lib/alglie.gd
@@ -514,6 +514,11 @@ DeclareAttribute( "LieSolvableRadical", IsAlgebra and IsLieAlgebra );
## Lie algebras.
## Then returns the type of L, i.e.,
## a string containing the types of the simple summands of L.
+## The field of L must not have characteristic 2 or 3, and the
+## Killing form of L must be nondegenerate.
+## If L has characteristic 0, the structure constants of L
+## must be rational numbers; Lie algebras over arbitrary characteristic
+## 0 fields are not supported.
## L:= SimpleLieAlgebra( "E", 8, Rationals );;
## gap> b:= BasisVectors( Basis( L ) );;
diff --git a/lib/alglie.gi b/lib/alglie.gi
index 322e003d6d..d682f71459 100644
--- a/lib/alglie.gi
+++ b/lib/alglie.gi
@@ -34,7 +34,7 @@ InstallMethod( LieUpperCentralSeries,
# under the natural homomorphism.
Add( S, C );
hom:= NaturalHomomorphismByIdeal( L, C );
- C:= PreImages( hom, LieCentre( Range( hom ) ) );
+ C:= PreImagesNC( hom, LieCentre( Range( hom ) ) );
#T we would like to get ideals!
#T is it possible to teach the hom. that the preimage of an ideal is an ideal?
@@ -1706,7 +1706,7 @@ InstallMethod( LieSolvableRadical,
quo:= ImagesSource( hom );
r1:= LieSolvableRadical( quo );
B:= BasisVectors( Basis( r1 ) );
- B:= List( B, x -> PreImagesRepresentative( hom, x ) );
+ B:= List( B, x -> PreImagesRepresentativeNC( hom, x ) );
Append( B, BasisVectors( Basis( n ) ) );
fi;
@@ -2092,7 +2092,7 @@ InstallMethod( DirectSumDecomposition,
SetRadicalOfAlgebra( Q, Subalgebra( Q, [ Zero( Q ) ] ) );
id:= List( CentralIdempotentsOfAlgebra( Q ),
- x->PreImagesRepresentative(hom,x));
+ x->PreImagesRepresentativeNC(hom,x));
# Now we lift the idempotents to the big algebra `A'. The
# first idempotent is lifted as follows:
@@ -4017,9 +4017,10 @@ InstallMethod( ImagesRepresentative,
###########################################################################
##
+#M PreImagesRepresentativeNC( f, x )
#M PreImagesRepresentative( f, x )
##
-InstallMethod( PreImagesRepresentative,
+InstallMethod( PreImagesRepresentativeNC,
"for Fp to SCA mapping, and element",
FamRangeEqFamElm,
[ IsFptoSCAMorphism, IsSCAlgebraObj ], 0,
@@ -4095,6 +4096,19 @@ InstallMethod( PreImagesRepresentative,
end);
+InstallMethod( PreImagesRepresentative,
+ "for Fp to SCA mapping, and element",
+ FamRangeEqFamElm,
+ [ IsFptoSCAMorphism, IsSCAlgebraObj ], 0,
+
+ function( f, x )
+ if not ( x in Range( f ) ) then
+ return fail;
+ fi;
+ return PreImagesRepresentative( f, x );
+
+end );
+
#############################################################################
##
#M Dimension( )
@@ -5592,8 +5606,8 @@ InstallMethod( JenningsLieAlgebra,
T:= EmptySCTable( dim , Zero(F) , "antisymmetric" );
pimgs := [];
for i in [1..dim] do
- a:= PreImagesRepresentative( Homs[pos[i]] ,
- PreImagesRepresentative( hom_pcg[pos[i]], gens[i] ) );
+ a:= PreImagesRepresentativeNC( Homs[pos[i]] ,
+ PreImagesRepresentativeNC( hom_pcg[pos[i]], gens[i] ) );
# calculate the p-th power image of `a':
@@ -5610,8 +5624,8 @@ InstallMethod( JenningsLieAlgebra,
# Calculate the commutator [a,b], and map the result into
# the correct homogeneous component.
- b:= PreImagesRepresentative( Homs[pos[j]],
- PreImagesRepresentative( hom_pcg[pos[j]], gens[j] ));
+ b:= PreImagesRepresentativeNC( Homs[pos[j]],
+ PreImagesRepresentativeNC( hom_pcg[pos[j]], gens[j] ));
c:= Image( hom_pcg[pos[i] + pos[j]],
Image(Homs[pos[i] + pos[j]], a^-1*b^-1*a*b) );
e:= ExtRepOfObj(c);
@@ -5788,8 +5802,8 @@ InstallMethod( PCentralLieAlgebra,
T:= EmptySCTable( dim , Zero(F) , "antisymmetric" );
pimgs := [];
for i in [1..dim] do
- a:= PreImagesRepresentative( Homs[pos[i]] ,
- PreImagesRepresentative( hom_pcg[pos[i]], gens[i] ) );
+ a:= PreImagesRepresentativeNC( Homs[pos[i]] ,
+ PreImagesRepresentativeNC( hom_pcg[pos[i]], gens[i] ) );
# calculate the p-th power image of `a':
@@ -5807,8 +5821,8 @@ InstallMethod( PCentralLieAlgebra,
# Calculate the commutator [a,b], and map the result into
# the correct homogeneous component.
- b:= PreImagesRepresentative( Homs[pos[j]],
- PreImagesRepresentative( hom_pcg[pos[j]], gens[j] ));
+ b:= PreImagesRepresentativeNC( Homs[pos[j]],
+ PreImagesRepresentativeNC( hom_pcg[pos[j]], gens[j] ));
c:= Image( hom_pcg[pos[i] + pos[j]],
Image(Homs[pos[i] + pos[j]], a^-1*b^-1*a*b) );
e:= ExtRepOfObj(c);
diff --git a/lib/algrep.gi b/lib/algrep.gi
index 8d331feee2..7607190b94 100644
--- a/lib/algrep.gi
+++ b/lib/algrep.gi
@@ -1212,24 +1212,24 @@ InstallMethod( NaturalHomomorphismBySubAlgebraModule,
if IsLeftAlgebraModuleElementCollection( V ) then
if IsRightAlgebraModuleElementCollection( V ) then
left_op:= function( x, v )
- return ImagesRepresentative( f, x^PreImagesRepresentative( f, v ) );
+ return ImagesRepresentative( f, x^PreImagesRepresentativeNC( f, v ) );
end;
right_op:= function( v, x )
- return ImagesRepresentative( f, PreImagesRepresentative( f, v )^x );
+ return ImagesRepresentative( f, PreImagesRepresentativeNC( f, v )^x );
end;
qmod:= BiAlgebraModule( LeftActingAlgebra( V ),
RightActingAlgebra( V ),
left_op, right_op, quot );
else
left_op:= function( x, v )
- return ImagesRepresentative( f, x^PreImagesRepresentative( f, v ) );
+ return ImagesRepresentative( f, x^PreImagesRepresentativeNC( f, v ) );
end;
qmod:= LeftAlgebraModule( LeftActingAlgebra( V ),
left_op, quot);
fi;
else
right_op:= function( v, x )
- return ImagesRepresentative( f, PreImagesRepresentative( f, v )^x );
+ return ImagesRepresentative( f, PreImagesRepresentativeNC( f, v )^x );
end;
qmod:= RightAlgebraModule( RightActingAlgebra( V ),
right_op, quot );
diff --git a/lib/autsr.gi b/lib/autsr.gi
index 241cc84115..704f9093dc 100644
--- a/lib/autsr.gi
+++ b/lib/autsr.gi
@@ -118,7 +118,7 @@ local C,M,p,all,gens,sub,q,hom,fp,rels,new,pre,i,free,cnt;
rels:=Filtered(RelatorsOfFpGroup(fp),x->ForAll(ExponentSums(x),x->x mod p=0));
rels:=List(rels,x->ElementOfFpGroup(FamilyObj(One(fp)),x));
new:=RestrictedMapping(nat,C)*hom;
- pre:=List(rels,x->PreImagesRepresentative(new,x));
+ pre:=List(rels,x->PreImagesRepresentativeNC(new,x));
for i in [1..Length(rels)] do
if not pre[i] in sub then
Add(all,MappedWord(rels[i],
@@ -141,7 +141,7 @@ local ocr,fphom,fpg,free,len,dim,tmp,L0,R,rels,mat,r,RS,i,g,v,cnt;
fpg:=FreeGeneratorsOfFpGroup(Range(fphom));
ocr.factorpres:=[fpg,RelatorsOfFpGroup(Range(fphom))];
ocr.generators:=List(GeneratorsOfGroup(Range(fphom)),
- i->PreImagesRepresentative(fphom,i));
+ i->PreImagesRepresentativeNC(fphom,i));
OCAddMatrices(ocr,ocr.generators);
OCAddRelations(ocr,ocr.generators);
OCAddSumMatrices(ocr,ocr.generators);
@@ -274,8 +274,8 @@ BindGlobal("AGSRAutomLift",function(ocr,nat,fhom,miso)
# allow to deduce corresponding module aut.
t:=ocr.trickrels;
phom:=IdentityMapping(ocr.moduleauts);
- s:=List(t.gens,x->PreImagesRepresentative(nat,x));
- l:=List(t.gens,x->PreImagesRepresentative(nat,ImagesRepresentative(fhom,x)));
+ s:=List(t.gens,x->PreImagesRepresentativeNC(nat,x));
+ l:=List(t.gens,x->PreImagesRepresentativeNC(nat,ImagesRepresentative(fhom,x)));
s:=List(t.rels,x->MappedWord(x,GeneratorsOfGroup(t.free),s));
l:=List(t.rels,x->MappedWord(x,GeneratorsOfGroup(t.free),l));
@@ -294,7 +294,7 @@ BindGlobal("AGSRAutomLift",function(ocr,nat,fhom,miso)
Size(Image(phom)));
fi;
for ep in enum do
- e:=PreImagesRepresentative(phom,ep);
+ e:=PreImagesRepresentativeNC(phom,ep);
psim:=e*miso;
psim:=psim^-1;
w:=-List(v,i->i*psim);
@@ -486,7 +486,7 @@ local S,c,hom,q,a,b,i,t,have,ups,new,u,good,abort,clim,worked,pp,
cnt:=0;
for b in t do
- new:=PreImagesRepresentative(hom,b);
+ new:=PreImagesRepresentativeNC(hom,b);
if (pp=false or new^pp in S) and locond(new) then
S:=ClosureGroup(S,new);
have:=true;
@@ -1028,7 +1028,7 @@ local ff,r,d,ser,u,v,i,j,k,p,bd,e,gens,lhom,M,N,hom,Q,Mim,q,ocr,split,MPcgs,
b:=MTX.BasisRadical(mo);
fratsim:=Length(b)=0;
if not fratsim then
- b:=List(b,x->PreImagesRepresentative(hom,PcElementByExponents(MPcgs,x)));
+ b:=List(b,x->PreImagesRepresentativeNC(hom,PcElementByExponents(MPcgs,x)));
for j in b do
N:=ClosureSubgroup(N,b);
od;
@@ -1129,8 +1129,8 @@ local ff,r,d,ser,u,v,i,j,k,p,bd,e,gens,lhom,M,N,hom,Q,Mim,q,ocr,split,MPcgs,
if perm in Aperm then
return true;
fi;
- aut:=PreImagesRepresentative(AQiso,perm);
- newgens:=List(gens,x->PreImagesRepresentative(comiso,
+ aut:=PreImagesRepresentativeNC(AQiso,perm);
+ newgens:=List(gens,x->PreImagesRepresentativeNC(comiso,
ImagesRepresentative(aut,ImagesRepresentative(comiso,x))));
mo2:=GModuleByMats(LinearActionLayer(newgens,MPcgs),mo.field);
@@ -1163,9 +1163,9 @@ local ff,r,d,ser,u,v,i,j,k,p,bd,e,gens,lhom,M,N,hom,Q,Mim,q,ocr,split,MPcgs,
if perm in Aperm then
return true;
fi;
- aut:=PreImagesRepresentative(AQiso,perm);
+ aut:=PreImagesRepresentativeNC(AQiso,perm);
newgens:=List(GeneratorsOfGroup(Q),
- x->PreImagesRepresentative(q,Image(aut,ImagesRepresentative(q,x))));
+ x->PreImagesRepresentativeNC(q,Image(aut,ImagesRepresentative(q,x))));
mo2:=GModuleByMats(LinearActionLayer(newgens,MPcgs),mo.field);
return MTX.IsomorphismModules(mo,mo2)<>fail;
end;
@@ -1175,9 +1175,9 @@ local ff,r,d,ser,u,v,i,j,k,p,bd,e,gens,lhom,M,N,hom,Q,Mim,q,ocr,split,MPcgs,
if perm in Aperm then
return true;
fi;
- aut:=PreImagesRepresentative(AQiso,perm);
+ aut:=PreImagesRepresentativeNC(AQiso,perm);
newgens:=List(GeneratorsOfGroup(Q),
- x->PreImagesRepresentative(q,Image(aut,ImagesRepresentative(q,x))));
+ x->PreImagesRepresentativeNC(q,Image(aut,ImagesRepresentative(q,x))));
mo2:=GModuleByMats(LinearActionLayer(newgens,MPcgs),mo.field);
iso:=MTX.IsomorphismModules(mo,mo2);
if iso=fail then
@@ -1234,12 +1234,12 @@ local ff,r,d,ser,u,v,i,j,k,p,bd,e,gens,lhom,M,N,hom,Q,Mim,q,ocr,split,MPcgs,
# stabilize class
k:=SmallGeneratingSet(sub);
ac:=OrbitStabilizerAlgorithm(sub,false,false,
- k,List(k,x->PreImagesRepresentative(AQiso,x)),
+ k,List(k,x->PreImagesRepresentativeNC(AQiso,x)),
rec(pnt:=j,
act:=
function(set,phi)
#local phi;
- #phi:=PreImagesRepresentative(AQiso,perm);
+ #phi:=PreImagesRepresentativeNC(AQiso,perm);
return Set(List(set,x->Image(phi,x)));
end,
onlystab:=true));
@@ -1367,7 +1367,7 @@ local ff,r,d,ser,u,v,i,j,k,p,bd,e,gens,lhom,M,N,hom,Q,Mim,q,ocr,split,MPcgs,
GeneratorsOfGroup(rf),
List(GeneratorsOfGroup(rf),
y->ImagesRepresentative(hom,ImagesRepresentative(j,
- PreImagesRepresentative(hom,y)))));
+ PreImagesRepresentativeNC(hom,y)))));
Assert(2,IsBijective(k));
Add(ind,k);
od;
@@ -1390,7 +1390,7 @@ local ff,r,d,ser,u,v,i,j,k,p,bd,e,gens,lhom,M,N,hom,Q,Mim,q,ocr,split,MPcgs,
proj:=GroupHomomorphismByImagesNC(AQP,Image(resperm),
B[2],List(GeneratorsOfGroup(res),x->ImagesRepresentative(resperm,x)));
C:=PreImage(proj,Image(resperm,ind));
- C:=List(SmallGeneratingSet(C),x->PreImagesRepresentative(AQiso,x));
+ C:=List(SmallGeneratingSet(C),x->PreImagesRepresentativeNC(AQiso,x));
AQ:=Group(C);
SetIsFinite(AQ,true);
SetIsGroupOfAutomorphismsFiniteGroup(AQ,true);
@@ -1416,7 +1416,7 @@ local ff,r,d,ser,u,v,i,j,k,p,bd,e,gens,lhom,M,N,hom,Q,Mim,q,ocr,split,MPcgs,
C:=MappingGeneratorsImages(AQiso);
if C[2]<>GeneratorsOfGroup(AQP) then
C:=[List(GeneratorsOfGroup(AQP),
- x->PreImagesRepresentative(AQiso,x)),
+ x->PreImagesRepresentativeNC(AQiso,x)),
GeneratorsOfGroup(AQP)];
fi;
for j in u do
@@ -1450,7 +1450,7 @@ local ff,r,d,ser,u,v,i,j,k,p,bd,e,gens,lhom,M,N,hom,Q,Mim,q,ocr,split,MPcgs,
substb:=SmallGeneratingSet(substb);
AQP:=Group(substb);
SetSize(AQP,B);
- C:=[List(substb,x->PreImagesRepresentative(AQiso,x)),substb];
+ C:=[List(substb,x->PreImagesRepresentativeNC(AQiso,x)),substb];
fi;
od;
@@ -1883,7 +1883,7 @@ local d,a,map,cG,nG,nH,i,j,u,v,asAutomorphism,K,L,conj,e1,e2,
else
gens:=SmallGeneratingSet(api);
fi;
- pre:=List(gens,x->PreImagesRepresentative(iso,x));
+ pre:=List(gens,x->PreImagesRepresentativeNC(iso,x));
map:=RepresentativeAction(SubgroupNC(a,pre),u,v,asAutomorphism);
if map=fail then
return fail;
@@ -1904,6 +1904,6 @@ local d,a,map,cG,nG,nH,i,j,u,v,asAutomorphism,K,L,conj,e1,e2,
fi;
return GroupHomomorphismByImagesNC(G,H,GeneratorsOfGroup(G),
- List(GeneratorsOfGroup(G),x->PreImagesRepresentative(e2,
+ List(GeneratorsOfGroup(G),x->PreImagesRepresentativeNC(e2,
Image(conj,Image(e1,x)))));
end);
diff --git a/lib/clas.gi b/lib/clas.gi
index b933b7d50b..2a27e3cbba 100644
--- a/lib/clas.gi
+++ b/lib/clas.gi
@@ -395,7 +395,7 @@ local H,cl,a,c;
H:=Image(hom,G);
cl:=[];
for c in ConjugacyClasses(H) do
- a:=ConjugacyClass(G,PreImagesRepresentative(hom,Representative(c)));
+ a:=ConjugacyClass(G,PreImagesRepresentativeNC(hom,Representative(c)));
if HasStabilizerOfExternalSet(c) then
SetStabilizerOfExternalSet(a,PreImage(hom,StabilizerOfExternalSet(c)));
fi;
diff --git a/lib/clashom.gi b/lib/clashom.gi
index 201b2cd9b7..16c7c4f9c3 100644
--- a/lib/clashom.gi
+++ b/lib/clashom.gi
@@ -499,7 +499,7 @@ local clT, # classes T
for k in clop do
Info(InfoHomClass,1,"lifting class ",Representative(k));
- r:=PreImagesRepresentative(ophom,Representative(k));
+ r:=PreImagesRepresentativeNC(ophom,Representative(k));
# try to make r of small order
rp:=r^Order(Representative(k));
rp:=RepresentativeAction(M,Concatenation(components),
@@ -564,7 +564,7 @@ local clT, # classes T
orb:=[];
for p in [1..Length(clTR)] do
- repres:=PreImagesRepresentative(projections[i],clTR[p]);
+ repres:=PreImagesRepresentativeNC(projections[i],clTR[p]);
if i=1 or isdirprod
or reps[j]*RestrictedPermNC(repres,components[i])
in Mproj[i] then
@@ -586,8 +586,8 @@ local clT, # classes T
#was:
#clTR:=List(clTR,i->ConjugacyClass(localcent_r,i));
- #clTR:=List(clTR,j->[PreImagesRepresentative(projections[i],
- # Representative(j)),
+ #clTR:=List(clTR,j->[PreImagesRepresentativeNC(projections[i],
+ # Representative(j)),
# PreImage(centrhom,Centralizer(j)),
# j]);
@@ -706,7 +706,7 @@ local clT, # classes T
#change the transversal element to map to the representative
con:=trans[orpo]*gen;
limg:=opfun(repres,con);
- con:=con*PreImagesRepresentative(centrhom,
+ con:=con*PreImagesRepresentativeNC(centrhom,
RepresentativeAction(localcent_r,
Image(projections[i],limg),
Representative(clTR[p][3])));
@@ -798,7 +798,7 @@ local clT, # classes T
# centralizers_r-conjugation.)
con:=trans[orpo]*gen;
limg:=opfun(repres,con);
- con:=con*PreImagesRepresentative(centrhom,
+ con:=con*PreImagesRepresentativeNC(centrhom,
RepresentativeAction(localcent_r,
Image(projections[i],limg),
Representative(orb[p][3])));
@@ -870,7 +870,7 @@ local clT, # classes T
# remember the element to try
trymap:=[p,(cengen[genpos2]*
- PreImagesRepresentative(
+ PreImagesRepresentativeNC(
RestrictedMapping(projections[i],
centralizers[j]),
RepresentativeAction(
@@ -1140,7 +1140,7 @@ local cs, # chief series of G
# compute the classes of the simple nonabelian factor by random search
hom:=NaturalHomomorphismByNormalSubgroupNC(G,lastM);
cl:=ConjugacyClasses(Image(hom));
- cl:=List(cl,i->[PreImagesRepresentative(hom,Representative(i)),
+ cl:=List(cl,i->[PreImagesRepresentativeNC(hom,Representative(i)),
PreImage(hom,StabilizerOfExternalSet(i))]);
cs:=Concatenation([G],Filtered(cs,x->IsSubset(lastM,x)));
fi;
@@ -1207,7 +1207,7 @@ local cs, # chief series of G
autos:=List(GeneratorsOfGroup(G),
i->GroupHomomorphismByImagesNC(T1,T1,GeneratorsOfGroup(T1),
List(GeneratorsOfGroup(T1),
- j->Image(Thom,PreImagesRepresentative(Thom,j)^i))));
+ j->Image(Thom,PreImagesRepresentativeNC(Thom,j)^i))));
# find (probably another) permutation rep for T1 for which all
# automorphisms can be represented by permutations
@@ -1268,7 +1268,7 @@ local cs, # chief series of G
autos:=List(GeneratorsOfGroup(S),
i->GroupHomomorphismByImagesNC(T1,T1,GeneratorsOfGroup(T1),
List(GeneratorsOfGroup(T1),
- j->Image(Thom,PreImagesRepresentative(Thom,j)^i))));
+ j->Image(Thom,PreImagesRepresentativeNC(Thom,j)^i))));
# find (probably another) permutation rep for T1 for which all
# automorphisms can be represented by permutations
@@ -1288,7 +1288,7 @@ local cs, # chief series of G
# define isomorphisms between the components
reps:=List([1..n],i->
- PreImagesRepresentative(Qhom,RepresentativeAction(Q,1,i)));
+ PreImagesRepresentativeNC(Qhom,RepresentativeAction(Q,1,i)));
genimages:=[];
for j in GeneratorsOfGroup(G) do
@@ -1345,7 +1345,7 @@ local cs, # chief series of G
SetSize(F,Size(G));
FM:=GroupHomomorphismByImagesNC(G,F,GeneratorsOfGroup(G),FM);
clF:=ConjugacyClassesFittingFreeGroup(F);
- clF:=List(clF,x->[PreImagesRepresentative(FM,x[1]),PreImage(FM,x[2])]);
+ clF:=List(clF,x->[PreImagesRepresentativeNC(FM,x[1]),PreImage(FM,x[2])]);
return clF;
fi;
#fi;
@@ -1374,9 +1374,9 @@ local cs, # chief series of G
Info(InfoHomClass,1,
"homomorphism is faithful for relevant factor, take preimages");
if Size(N)=1 and onlysizes=true then
- cl:=List(clF,i->[PreImagesRepresentative(Fhom,i[1]),Size(i[2])]);
+ cl:=List(clF,i->[PreImagesRepresentativeNC(Fhom,i[1]),Size(i[2])]);
else
- cl:=List(clF,i->[PreImagesRepresentative(Fhom,i[1]),
+ cl:=List(clF,i->[PreImagesRepresentativeNC(Fhom,i[1]),
PreImage(Fhom,i[2])]);
fi;
else
@@ -1391,7 +1391,7 @@ local cs, # chief series of G
for k in clF do
# modify the representative with a kernel elm. to project
# correctly on the second component
- elm:=j[1]*PreImagesRepresentative(FMhom,
+ elm:=j[1]*PreImagesRepresentativeNC(FMhom,
LeftQuotient(Image(Fhom,j[1]),k[1]));
zentr:=Intersection(j[2],PreImage(Fhom,k[2]));
Assert(3,ForAll(GeneratorsOfGroup(zentr),
@@ -1449,7 +1449,7 @@ local cs, # chief series of G
if Image(Qhom,elm)=jim then
# modify the representative with a kernel elm. to project
# correctly on the second component
- elm:=l[1]*PreImagesRepresentative(FMhom,
+ elm:=l[1]*PreImagesRepresentativeNC(FMhom,
LeftQuotient(Image(Fhom,l[1]),elm));
zentr:=PreImage(Fhom,k[2]^l1);
zentr:=Intersection(zentr,l[2]);
@@ -1957,7 +1957,7 @@ local classes, # classes to be constructed, the result
c := [h * PcElementByExponentsNC( Npcgs,w*com.factorspace),
stabrad,stabfacgens,stabfacimg,subsz,stabrsubsz];
#if reduce<>fail then
- # Add(classes,[PreImagesRepresentative(reduce,c[1]),
+ # Add(classes,[PreImagesRepresentativeNC(reduce,c[1]),
# PreImage(reduce,c[2])]);
# else
@@ -2022,7 +2022,7 @@ BindGlobal("LiftClassesEATrivRep",
nsfgens:=NormalIntersection(fants[usent],Group(cl[4]));
fasize:=Size(nsfgens);
nsfgens:=SmallGeneratingSet(nsfgens);
- nsgens:=List(nsfgens,x->PreImagesRepresentative(hom,x));
+ nsgens:=List(nsfgens,x->PreImagesRepresentativeNC(hom,x));
nsimgs:=List(Concatenation(pcgs,nsgens),npcgsact);
mo:=GModuleByMats(nsimgs,field);
if not MTX.IsIrreducible(mo) then
@@ -2338,7 +2338,7 @@ local r, #radical
if IsPermGroup(Range(hom)) and not IsPermGroup(Source(hom)) then
f:=Image(hom,G);
cl:=ConjugacyClassesFittingFreeGroup(f:onlysizes:=false);
- cl:=List(cl,x->[PreImagesRepresentative(hom,x[1]),
+ cl:=List(cl,x->[PreImagesRepresentativeNC(hom,x[1]),
PreImage(hom,x[2])]);
else
cl:=ConjugacyClassesFittingFreeGroup(G:onlysizes:=false);
@@ -2398,12 +2398,12 @@ local r, #radical
if ntrihom then
ncl:=[];
for i in cl do
- new:=[PreImagesRepresentative(hom,i[1])];
+ new:=[PreImagesRepresentativeNC(hom,i[1])];
if not IsInt(i[2]) then
Add(new,[]); # no generators in radical yet
gens:=SmallGeneratingSet(i[2]);
Add(new,
- List(gens,x->PreImagesRepresentative(hom,x)));
+ List(gens,x->PreImagesRepresentativeNC(hom,x)));
Add(new,gens);
#TODO: PreImage groups?
#Add(new,PreImage(hom,i[2]));
@@ -2886,10 +2886,10 @@ local r, #radical
fi;
prereps:=f!.classpreimgs;
if not IsBound(prereps[j]) then
- prereps[j]:=PreImagesRepresentative(hom,Representative(cl[j]));
+ prereps[j]:=PreImagesRepresentativeNC(hom,Representative(cl[j]));
fi;
- r:=PreImagesRepresentative(hom,conj);
+ r:=PreImagesRepresentativeNC(hom,conj);
d:=GeneratorsOfGroup(Centralizer(cl[j]));
# Format for cl is:
@@ -2897,7 +2897,7 @@ local r, #radical
# in factor, 4:conjugator, 5:cenpcgs,
# 6:cenfac, 7:cenfacimgs, 8:censize, 9:cenfacsize
Add(nreps,[i,i^r,prereps[j],r,[],
- List(d,x->PreImagesRepresentative(hom,x)),d,
+ List(d,x->PreImagesRepresentativeNC(hom,x)),d,
radsize*Size(Centralizer(cl[j])), Size(Centralizer(cl[j]))]);
od;
reps:=nreps;
diff --git a/lib/csetgrp.gi b/lib/csetgrp.gi
index 9c5955a8f3..c2d37bfba8 100644
--- a/lib/csetgrp.gi
+++ b/lib/csetgrp.gi
@@ -199,7 +199,7 @@ local cla,clb,i,j,k,bd,r,rep,b2,dc,
r:=SmallerDegreePermutationRepresentation(b:cheap);
k:=Image(r,b);
gens:=MorFindGeneratingSystem(k,MorMaxFusClasses(MorRatClasses(k)));
- gens:=List(gens,x->PreImagesRepresentative(r,x));
+ gens:=List(gens,x->PreImagesRepresentativeNC(r,x));
else
gens:=MorFindGeneratingSystem(b,MorMaxFusClasses(MorRatClasses(b)));
fi;
@@ -1064,7 +1064,7 @@ local c, flip, maxidx, cano, tryfct, p, r, t,
Assert(2,Size(a2)*Size(tra)=Size(b));
SetKernelOfMultiplicativeGeneralMapping(r,a2);
- dcs:=List(dcs,x->[PreImagesRepresentative(quot,x[1]),Size(a1)*x[2],
+ dcs:=List(dcs,x->[PreImagesRepresentativeNC(quot,x[1]),Size(a1)*x[2],
PreImage(r,x[3])]);
r:=List(dcs,x->x[1]);
stabs:=List(dcs,x->x[3]);
diff --git a/lib/ctblfuns.gi b/lib/ctblfuns.gi
index c648c9401f..eec04e92e4 100644
--- a/lib/ctblfuns.gi
+++ b/lib/ctblfuns.gi
@@ -2049,8 +2049,8 @@ InstallMethod( InertiaSubgroup,
if stab = permgrp then
return G;
else
- return PreImagesSet( GroupHomomorphismByImages( G, permgrp,
- GeneratorsOfGroup( G ), perms ),
+ return PreImagesSetNC( GroupHomomorphismByImages( G, permgrp,
+ GeneratorsOfGroup( G ), perms ),
stab );
fi;
end );
diff --git a/lib/ctblgrp.gi b/lib/ctblgrp.gi
index 3b41dbb5be..914845923f 100644
--- a/lib/ctblgrp.gi
+++ b/lib/ctblgrp.gi
@@ -1606,7 +1606,7 @@ local tm,tme,piso,gpcgs,gals,ord,l,l2,f,fgens,rws,pow,pos,i,j,k,gen,
# not easily transfer to mod p.
k:=Image(piso,TrivialSubgroup(D.galMorphisms));
gpcgs:=Pcgs(k);
- gals:=List(gpcgs,i->PreImagesRepresentative(piso,i));
+ gals:=List(gpcgs,i->PreImagesRepresentativeNC(piso,i));
ord:=List(gpcgs,i->RelativeOrderOfPcElement(gpcgs,i));
l:=Length(gpcgs);
@@ -1827,7 +1827,7 @@ local often,trans,e,neu,i,inv,cent,l,s,s1,x,dom;
if dom=fail then
x:=D.classreps[inv];
- l:=List(s,i->[x^PreImagesRepresentative(e,
+ l:=List(s,i->[x^PreImagesRepresentativeNC(e,
RepresentativeAction(Image(e),1,i[1])),Size(cent)*Length(i)]);
else
l:=List(s,i->[dom[i[1]],Size(cent)*Length(i)]);
diff --git a/lib/ctblsolv.gi b/lib/ctblsolv.gi
index d18f10f6d7..fc787a2bb6 100644
--- a/lib/ctblsolv.gi
+++ b/lib/ctblsolv.gi
@@ -176,7 +176,7 @@ InstallGlobalFunction( ProjectiveCharDeg, function( G, z, q )
# `N' is a normal subgroup such that `N/' is a chief factor of `G'
# of order `i' which is a power of `p'.
- N:= PreImagesSet( h, N );
+ N:= PreImagesSetNC( h, N );
i:= Size( N ) / oz;
p:= Factors( i )[1];
@@ -184,7 +184,7 @@ InstallGlobalFunction( ProjectiveCharDeg, function( G, z, q )
# `c' is a list of complement classes of `N' modulo `z'
c:= List( ComplementClassesRepresentatives( ImagesSource( h ), ImagesSet( h, N ) ),
- x -> PreImagesSet( h, x ) );
+ x -> PreImagesSetNC( h, x ) );
r:= Centralizer( G, N );
for L in c do
if IsSubset( L, r ) then
@@ -563,7 +563,7 @@ InstallGlobalFunction( CoveringTriplesCharacters, function( G, z )
N:= ChiefSeriesUnderAction( img, N );
N:= N[ Length( N ) - 1 ];
fi;
- N:= PreImagesSet( h, N );
+ N:= PreImagesSetNC( h, N );
if not IsAbelian( N ) then
Info( InfoCharacterTable, 2,
@@ -582,9 +582,9 @@ InstallGlobalFunction( CoveringTriplesCharacters, function( G, z )
h:= NaturalHomomorphismByNormalSubgroupNC( G, P );
r:= List( CoveringTriplesCharacters( ImagesSource( h ),
ImageElm( h, z ) ),
- x -> [ PreImagesSet( h, x[1] ),
- PreImagesSet( h, x[2] ),
- PreImagesRepresentative( h, x[3] ) ] );
+ x -> [ PreImagesSetNC( h, x[1] ),
+ PreImagesSetNC( h, x[2] ),
+ PreImagesRepresentativeNC( h, x[3] ) ] );
if p = i then
@@ -622,9 +622,9 @@ InstallGlobalFunction( CoveringTriplesCharacters, function( G, z )
c:= Stabilizer( img, zn );
fi;
Append( r, List( CoveringTriplesCharacters( c, zn ),
- x -> [ PreImagesSet( h, x[1] ),
- PreImagesSet( h, x[2] ),
- PreImagesRepresentative( h, x[3] ) ] ) );
+ x -> [ PreImagesSetNC( h, x[1] ),
+ PreImagesSetNC( h, x[2] ),
+ PreImagesRepresentativeNC( h, x[3] ) ] ) );
od;
return r;
@@ -663,9 +663,9 @@ InstallGlobalFunction( CoveringTriplesCharacters, function( G, z )
img:= ImagesSource( h );
Append( r,
List( CoveringTriplesCharacters( img, ImageElm( h, z ) ),
- x -> [ PreImagesSet( h, x[1] ),
- PreImagesSet( h, x[2] ),
- PreImagesRepresentative( h, x[3] ) ] ) );
+ x -> [ PreImagesSetNC( h, x[1] ),
+ PreImagesSetNC( h, x[2] ),
+ PreImagesRepresentativeNC( h, x[3] ) ] ) );
fi;
od;
return r;
@@ -1067,7 +1067,7 @@ InstallMethod( BaumClausenInfo,
for i in [ 2 .. Length( ssr.ds ) ] do
j:= NaturalHomomorphismByNormalSubgroupNC( ssr.ds[ i-1 ], ssr.ds[i] );
Append( pcgs, List( SpecialPcgs( ImagesSource( j ) ),
- x -> PreImagesRepresentative( j, x ) ) );
+ x -> PreImagesRepresentativeNC( j, x ) ) );
od;
Append( pcgs, SpecialPcgs( Last(ssr.ds) ) );
G:= ImagesSource( hom );
@@ -1911,7 +1911,7 @@ InstallMethod( BaumClausenInfo,
k:= Pcgs( kernel );
pcgs:= PcgsByPcSequence( ElementsFamily( FamilyObj( kernel ) ),
Concatenation( List( pcgs,
- x -> PreImagesRepresentative( hom, x ) ),
+ x -> PreImagesRepresentativeNC( hom, x ) ),
k ) );
k:= ListWithIdenticalEntries( Length( k ), 0 );
diff --git a/lib/error.g b/lib/error.g
index de03ee813f..3a81bebffd 100644
--- a/lib/error.g
+++ b/lib/error.g
@@ -135,7 +135,8 @@ BIND_GLOBAL("PRETTY_PRINT_VARS", function(context)
end);
BIND_GLOBAL("WHERE", function(depth, context, activecontext, showlocals)
- local bottom, lastcontext, f, level, totaldepth, countcontext;
+ local bottom, lastcontext, f, level, totaldepth, countcontext,
+ prefixwidth, location;
if depth <= 0 then
return;
fi;
@@ -144,6 +145,7 @@ BIND_GLOBAL("WHERE", function(depth, context, activecontext, showlocals)
PrintTo(ERROR_OUTPUT, "called from read-eval loop ");
return;
fi;
+ PrintTo(ERROR_OUTPUT, "Stack trace:\n");
lastcontext := context;
totaldepth := 0;
countcontext := context;
@@ -151,14 +153,20 @@ BIND_GLOBAL("WHERE", function(depth, context, activecontext, showlocals)
totaldepth := totaldepth + 1;
countcontext := ParentLVars(countcontext);
od;
+ prefixwidth := Length(String(totaldepth));
level := 1;
while depth > 0 and context <> bottom do
- PRINT_CURRENT_STATEMENT(
+ location := PRINT_CURRENT_STATEMENT(
ERROR_OUTPUT,
context,
activecontext,
level,
- totaldepth);
+ prefixwidth);
+ if location <> fail then
+ PrintTo(ERROR_OUTPUT, "\n",
+ ListWithIdenticalEntries(prefixwidth+2, ' '),
+ "@ ", location[1], ":", location[2]);
+ fi;
if showlocals then
PRETTY_PRINT_VARS(context);
else
@@ -228,7 +236,7 @@ end);
#
Unbind(ErrorInner);
BIND_GLOBAL("ErrorInner", function(options, earlyMessage)
- local context, tracebackContext, mayReturnVoid, mayReturnObj,
+ local context, tracebackContext, mayReturnVoid,
lateMessage, x, prompt, res, errorLVars, errorTracebackLVars,
kernelErrorLVars, justQuit, printEarlyMessage,
printEarlyTraceback, printAutomaticTraceback, lastErrorStream;
@@ -262,17 +270,6 @@ BIND_GLOBAL("ErrorInner", function(options, earlyMessage)
mayReturnVoid := false;
fi;
- if IsBound(options.mayReturnObj) then
- mayReturnObj := options.mayReturnObj;
- if not mayReturnObj in [false, true] then
- PrintTo(ERROR_OUTPUT, "ErrorInner: option mayReturnObj must be true or false\n");
- LEAVE_ALL_NAMESPACES();
- JUMP_TO_CATCH(1);
- fi;
- else
- mayReturnObj := false;
- fi;
-
if IsBound(options.tracebackContext) then
tracebackContext := options.tracebackContext;
if not IsLVarsBag(tracebackContext) then
@@ -312,9 +309,6 @@ BIND_GLOBAL("ErrorInner", function(options, earlyMessage)
printAutomaticTraceback := function()
if IsBound(OnBreak) and IsFunction(OnBreak) then
- if OnBreak = Where or OnBreak = WhereWithVars then
- PrintTo(ERROR_OUTPUT, "Stack trace:\n");
- fi;
OnBreak();
fi;
end;
@@ -410,7 +404,7 @@ BIND_GLOBAL("ErrorInner", function(options, earlyMessage)
prompt := "brk> ";
fi;
if not justQuit then
- res := SHELL(context,mayReturnVoid,mayReturnObj,true,prompt,false);
+ res := SHELL(context,mayReturnVoid,false,true,prompt,false);
else
res := fail;
fi;
@@ -455,8 +449,7 @@ BIND_GLOBAL("ErrorNoReturn", function(arg)
rec(
context := ParentLVars(GetCurrentLVars()),
mayReturnVoid := false,
- mayReturnObj := false,
- lateMessage := "type 'quit;' to quit to outer loop",
+ lateMessage := "you can enter 'quit;' to quit to outer loop",
),
arg);
end);
diff --git a/lib/ffe.gd b/lib/ffe.gd
index 3eeddef057..aa93c7a24f 100644
--- a/lib/ffe.gd
+++ b/lib/ffe.gd
@@ -118,9 +118,9 @@
## ]]>
## Z(11,40);
-## Error, Conway Polynomial 11^40 will need to computed and might be slow
-## return to continue
-## *[1] Error( "Conway Polynomial ", p, "^", d, " will need to computed and might be slow\n", "return to continue" );
+## Error, Conway Polynomial 11^40 will need to be computed and might be slow
+## Stack trace:
+## *[1] Error( "Conway Polynomial ", p, "^", d, " will need to be computed and might be slow" );
## @ GAPROOT/lib/ffeconway.gi:81
## [2] FFECONWAY.SetUpConwayStuff( p, d );
## @ GAPROOT/lib/ffeconway.gi:140
@@ -128,8 +128,8 @@
## @ GAPROOT/lib/ffeconway.gi:167
## ( )
## called from read-eval loop at *stdin*:2
-## you can 'quit;' to quit to outer loop, or
-## you can 'return;' to continue
+## you can enter 'quit;' to quit to outer loop, or
+## you can enter 'return;' to continue
## brk>
## ]]>
##
diff --git a/lib/ffeconway.gi b/lib/ffeconway.gi
index fd6f5b721d..04555686d4 100644
--- a/lib/ffeconway.gi
+++ b/lib/ffeconway.gi
@@ -78,7 +78,7 @@ FFECONWAY.SetUpConwayStuff := function(p,d)
if not IsCheapConwayPolynomial(p,d) then
Error("Conway Polynomial ",p,"^",d,
- " will need to computed and might be slow\n", "return to continue");
+ " will need to be computed and might be slow");
fi;
cp := CoefficientsOfUnivariatePolynomial(ConwayPolynomial(p,d));
diff --git a/lib/field.gi b/lib/field.gi
index f5eadb8ede..6223cf0535 100644
--- a/lib/field.gi
+++ b/lib/field.gi
@@ -1315,15 +1315,16 @@ InstallMethod( ImagesSet,
#############################################################################
##
-#M PreImagesElm( , ) . . . . . . . . . . . . preimage of an elm
+#M PreImagesElmNC( , ) . . . . . . . . . . . . preimage of an elm
+#M PreImagesElm( , ) . . . . . . . . . . . . . preimage of an elm
##
-InstallMethod( PreImagesElm,
+InstallMethod( PreImagesElmNC,
"for field homomorphism and element",
FamRangeEqFamElm,
[ IsFieldHomomorphism, IsObject ],
function ( hom, elm )
if IsInjective( hom ) = 1 then
- return [ PreImagesRepresentative( hom, elm ) ];
+ return [ PreImagesRepresentativeNC( hom, elm ) ];
elif IsZero( elm ) then
return Source( hom );
else
@@ -1331,18 +1332,41 @@ InstallMethod( PreImagesElm,
fi;
end );
+InstallMethod( PreImagesElm,
+ "for field homomorphism and element",
+ FamRangeEqFamElm,
+ [ IsFieldHomomorphism, IsObject ],
+ function ( hom, elm )
+ if not (elm in Range(hom)) then
+ return fail;
+ fi;
+ return PreImagesElm( hom, elm );
+ end );
#############################################################################
##
-#M PreImagesSet( , ) . . . . . . . . . . . . . preimage of a set
+#M PreImagesSetNC
+#M PreImagesSet
##
-InstallMethod( PreImagesSet,
+InstallMethod( PreImagesSetNC,
"for field homomorphism and field",
CollFamRangeEqFamElms,
[ IsFieldHomomorphism, IsField ],
function ( hom, elms )
elms:= FieldByGenerators( List( GeneratorsOfField( elms ),
- gen -> PreImagesRepresentative( hom, gen ) ) );
+ gen -> PreImagesRepresentativeNC( hom, gen ) ) );
UseSubsetRelation( Source( hom ), elms );
return elms;
end );
+
+InstallMethod( PreImagesSet,
+ "for field homomorphism and field",
+ CollFamRangeEqFamElms,
+ [ IsFieldHomomorphism, IsField ],
+ function ( hom, elms )
+ if not IsSubset( Range(hom), elms ) then
+ return fail;
+ fi;
+ return PreImagesSet( hom, elms );
+ end );
+
diff --git a/lib/fitfree.gi b/lib/fitfree.gi
index d68681ea93..e8669473c0 100644
--- a/lib/fitfree.gi
+++ b/lib/fitfree.gi
@@ -54,10 +54,10 @@ local ffs,pcisom,rest,kpc,k,x,ker,r,pool,i,xx,pregens,iso;
rest:=GroupHomomorphismByImages(U,Range(ffs.factorhom),GeneratorsOfGroup(U),
List(GeneratorsOfGroup(U),x->ImagesRepresentative(ffs.factorhom,x)));
else
- RUN_IN_GGMBI:=true; # hack to skip Nice treatment
+ PushOptions( rec( Run_In_GGMBI:= true ) ); # hack to skip Nice treatment
rest:=GroupHomomorphismByImagesNC(U,Range(ffs.factorhom),GeneratorsOfGroup(U),
List(GeneratorsOfGroup(U),x->ImagesRepresentative(ffs.factorhom,x)));
- RUN_IN_GGMBI:=false;
+ PopOptions();
fi;
Assert(1,rest<>fail);
@@ -81,7 +81,7 @@ local ffs,pcisom,rest,kpc,k,x,ker,r,pool,i,xx,pregens,iso;
else
iso:=IsomorphismFpGroup(Image(rest,U));
pregens:=List(GeneratorsOfGroup(Range(iso)),x->
- PreImagesRepresentative(rest,PreImagesRepresentative(iso,x)));
+ PreImagesRepresentativeNC(rest,PreImagesRepresentativeNC(iso,x)));
# evaluate relators
pool:=List(RelatorsOfFpGroup(Range(iso)),
x->MappedWord(x,FreeGeneratorsOfFpGroup(Range(iso)),pregens));
@@ -91,7 +91,7 @@ local ffs,pcisom,rest,kpc,k,x,ker,r,pool,i,xx,pregens,iso;
iso:=IsomorphismFpGroup(Image(rest,U));
pregens:=List(GeneratorsOfGroup(Range(iso)),x->
- PreImagesRepresentative(rest,PreImagesRepresentative(iso,x)));
+ PreImagesRepresentativeNC(rest,PreImagesRepresentativeNC(iso,x)));
# evaluate relators
pool:=List(RelatorsOfFpGroup(Range(iso)),
x->MappedWord(x,FreeGeneratorsOfFpGroup(Range(iso)),pregens));
@@ -135,7 +135,7 @@ local ffs,pcisom,rest,kpc,k,x,ker,r,pool,i,xx,pregens,iso;
# od;
SetSize(U,Size(Image(rest))*Size(kpc));
k:=InducedPcgs(FamilyPcgs(Image(pcisom)),kpc);
- k:=List(k,x->PreImagesRepresentative(pcisom,x));
+ k:=List(k,x->PreImagesRepresentativeNC(pcisom,x));
k:=InducedPcgsByPcSequenceNC(ffs.pcgs,k);
ker:=SubgroupNC(G,k);
SetSize(ker,Size(kpc));
@@ -257,7 +257,7 @@ local ffs,hom,U,rest,ker,r,p,l,i,depths,pcisom,subsz,pcimgs;
pcimgs:=List(ipcgs,x->ImagesRepresentative(ffs.pcisom,x));
ker:=SubgroupNC(G,List(MinimalGeneratingSet(Group(pcimgs,One(Range(ffs.pcisom)))),
- x->PreImagesRepresentative(ffs.pcisom,x)));
+ x->PreImagesRepresentativeNC(ffs.pcisom,x)));
SetPcgs(ker,ipcgs);
if Length(ipcgs)=0 then
SetSize(ker,1);
@@ -276,9 +276,9 @@ local ffs,hom,U,rest,ker,r,p,l,i,depths,pcisom,subsz,pcimgs;
if IsPermGroup(U) and AssertionLevel()>1 then
rest:=GroupHomomorphismByImages(U,Range(hom),gens,imgs);
else
- RUN_IN_GGMBI:=true; # hack to skip Nice treatment
+ PushOptions( rec( Run_In_GGMBI:= true ) ); # hack to skip Nice treatment
rest:=GroupHomomorphismByImagesNC(U,Range(hom),gens,imgs);
- RUN_IN_GGMBI:=false;
+ PopOptions();
fi;
Assert(1,rest<>fail);
@@ -319,11 +319,11 @@ local ffs,hom,U,rest,ker,r,p,l,i,depths,pcisom,subsz,pcimgs;
else
r:=SubgroupNC(G,ipcgs);
fi;
- RUN_IN_GGMBI:=true;
+ PushOptions( rec( Run_In_GGMBI:= true ) );
pcisom:=GroupHomomorphismByImagesNC(r,
SubgroupNC(Range(ffs.pcisom),pcisom),
ipcgs,pcisom);
- RUN_IN_GGMBI:=false;
+ PopOptions();
fi;
r:=rec(inducedfrom:=ffs,
pcgs:=ipcgs,
@@ -916,13 +916,14 @@ local ser,hom,s,fphom,sf,sg,sp,fp,d,head,mran,nran,mpcgs,ocr,len,pcgs,gens;
s:=SylowSubgroup(Image(hom),prime);
fphom:=IsomorphismFpGroup(s);
fp:=Image(fphom);
- sf:=List(GeneratorsOfGroup(Image(fphom)),x->PreImagesRepresentative(fphom,x));
- sg:=List(sf,x->PreImagesRepresentative(hom,x));
+ sf:=List(GeneratorsOfGroup(Image(fphom)),
+ x->PreImagesRepresentativeNC(fphom,x));
+ sg:=List(sf,x->PreImagesRepresentativeNC(hom,x));
sp:=[];
- RUN_IN_GGMBI:=true; # hack to skip Nice treatment
+ PushOptions( rec( Run_In_GGMBI:= true ) ); # hack to skip Nice treatment
fphom:=GroupGeneralMappingByImagesNC(Group(sg,One(G)),fp,sg,
GeneratorsOfGroup(fp));
- RUN_IN_GGMBI:=false;
+ PopOptions();
@@ -939,9 +940,9 @@ local ser,hom,s,fphom,sf,sg,sp,fp,d,head,mran,nran,mpcgs,ocr,len,pcgs,gens;
Append(sp,mpcgs);
else
# extend presentation
- RUN_IN_GGMBI:=true; # hack to skip Nice treatment
+ PushOptions( rec( Run_In_GGMBI:= true ) ); # hack to skip Nice treatment
fphom:=LiftFactorFpHom(fphom,Source(fphom),false,mpcgs);
- RUN_IN_GGMBI:=false;
+ PopOptions();
fp:=Image(fphom);
sp:=Concatenation(sp,mpcgs);
fi;
@@ -953,10 +954,10 @@ local ser,hom,s,fphom,sf,sg,sp,fp,d,head,mran,nran,mpcgs,ocr,len,pcgs,gens;
gens:=GeneratorsOfGroup(ocr.complement);
sg:=gens{[1..Length(sg)]};
sp:=gens{[Length(sg)+1..Length(gens)]};
- RUN_IN_GGMBI:=true; # hack to skip Nice treatment
+ PushOptions( rec( Run_In_GGMBI:= true ) ); # hack to skip Nice treatment
fphom:=GroupGeneralMappingByImagesNC(ocr.complement,fp,gens,
GeneratorsOfGroup(fp));
- RUN_IN_GGMBI:=false;
+ PopOptions();
fi;
od;
@@ -1194,7 +1195,7 @@ local s,d,c,act,o,i,j,h,p,hf,img,n,k,ns,all,hl,hcomp,
norm:=n);
for j in [2..Length(i)] do
c[i[j]]:=rec(orbit:=i,orbitpos:=j,
- rep:=PreImagesRepresentative(act,
+ rep:=PreImagesRepresentativeNC(act,
RepresentativeAction(Image(act),i[1],i[j])),
component:=d[i[j]],hall:=h, norm:=n);
od;
@@ -1232,7 +1233,7 @@ local s,d,c,act,o,i,j,h,p,hf,img,n,k,ns,all,hl,hcomp,
fp:=Range(fphom);
gens:=MappingGeneratorsImages(fphom);
imgs:=gens[2];gens:=gens[1];
- gens:=List(gens,x->PreImagesRepresentative(act,x));
+ gens:=List(gens,x->PreImagesRepresentativeNC(act,x));
# adapt to normalize B
gens:=List(gens,x->x/RepresentativeAction(t,b^x,b));
@@ -1240,11 +1241,11 @@ local s,d,c,act,o,i,j,h,p,hf,img,n,k,ns,all,hl,hcomp,
# now do complements one by one
for j in [1..Length(pcgs)] do
h:=ClosureGroup(dser[j],gens);
- RUN_IN_GGMBI:=true; # hack to skip Nice treatment
+ PushOptions( rec( Run_In_GGMBI:= true ) ); # hack to skip Nice treatment
fphom:=GroupGeneralMappingByImagesNC(h,fp,
Concatenation(GeneratorsOfGroup(dser[j]),gens),
Concatenation(List(GeneratorsOfGroup(dser[j]),x->One(fp)),imgs));
- RUN_IN_GGMBI:=false;
+ PopOptions();
ocr:=rec(group:=h,modulePcgs:=pcgs[j],
factorfphom:=fphom);
@@ -1256,18 +1257,18 @@ local s,d,c,act,o,i,j,h,p,hf,img,n,k,ns,all,hl,hcomp,
if Size(b)>Size(s) then
h:=ClosureGroup(b,gens);
- RUN_IN_GGMBI:=true; # hack to skip Nice treatment
+ PushOptions( rec( Run_In_GGMBI:= true ) ); # hack to skip Nice treatment
fphom:=GroupGeneralMappingByImagesNC(h,fp,
Concatenation(GeneratorsOfGroup(b),gens),
Concatenation(List(GeneratorsOfGroup(b),x->One(fp)),imgs));
- RUN_IN_GGMBI:=false;
+ PopOptions();
# get elementary abelian series from b to s
dser:=elabser(b,s);
pcgs:=List([2..Length(dser)],x->ModuloPcgs(dser[x-1],dser[x]));
for j in pcgs do
- RUN_IN_GGMBI:=true; # hack to skip Nice treatment
+ PushOptions( rec( Run_In_GGMBI:= true ) ); # hack to skip Nice treatment
fphom:=LiftFactorFpHom(fphom,Source(fphom),false,j);
- RUN_IN_GGMBI:=false;
+ PopOptions();
od;
gens:=MappingGeneratorsImages(fphom);
imgs:=gens[2];gens:=gens[1];
@@ -1280,7 +1281,7 @@ local s,d,c,act,o,i,j,h,p,hf,img,n,k,ns,all,hl,hcomp,
fp:=Image(fphom);
gens:=MappingGeneratorsImages(fphom);
imgs:=gens[2];gens:=gens[1];
- gens:=List(gens,x->PreImagesRepresentative(hom,x));
+ gens:=List(gens,x->PreImagesRepresentativeNC(hom,x));
fi;
# now run through the candidates for Hall in S
@@ -1325,12 +1326,12 @@ local s,d,c,act,o,i,j,h,p,hf,img,n,k,ns,all,hl,hcomp,
# now do complement to NS(k)/k
for z in [1..Length(pcgs)] do
h:=ClosureGroup(dser[z],cgens);
- RUN_IN_GGMBI:=true; # hack to skip Nice treatment
+ PushOptions( rec( Run_In_GGMBI:= true ) ); # hack to skip Nice treatment
fphom:=GroupGeneralMappingByImagesNC(h,fp,
Concatenation(GeneratorsOfGroup(dser[z]),cgens),
Concatenation(List(GeneratorsOfGroup(dser[z]),x->One(fp)),
imgs));
- RUN_IN_GGMBI:=false;
+ PopOptions();
ocr:=rec(group:=h,modulePcgs:=pcgs[z],
factorfphom:=fphom);
@@ -1408,13 +1409,14 @@ local ser,hom,s,fphom,sf,sg,sp,fp,d,head,mran,nran,mpcgs,ocr,len,pcgs,
for s in HallsFittingFree(Image(hom),pi) do
fphom:=IsomorphismFpGroup(s);
fp:=Image(fphom);
- sf:=List(GeneratorsOfGroup(Image(fphom)),x->PreImagesRepresentative(fphom,x));
- sg:=List(sf,x->PreImagesRepresentative(hom,x));
+ sf:=List(GeneratorsOfGroup(Image(fphom)),
+ x->PreImagesRepresentativeNC(fphom,x));
+ sg:=List(sf,x->PreImagesRepresentativeNC(hom,x));
sp:=[];
- RUN_IN_GGMBI:=true; # hack to skip Nice treatment
+ PushOptions( rec( Run_In_GGMBI:= true ) ); # hack to skip Nice treatment
fphom:=GroupGeneralMappingByImagesNC(Group(sg,One(G)),fp,sg,
GeneratorsOfGroup(fp));
- RUN_IN_GGMBI:=false;
+ PopOptions();
for d in [2..Length(ser.depths)] do
mran:=[ser.depths[d-1]..len];
@@ -1429,9 +1431,9 @@ local ser,hom,s,fphom,sf,sg,sp,fp,d,head,mran,nran,mpcgs,ocr,len,pcgs,
Append(sp,mpcgs);
else
# extend presentation
- RUN_IN_GGMBI:=true; # hack to skip Nice treatment
+ PushOptions( rec( Run_In_GGMBI:= true ) ); # hack to skip Nice treatment
fphom:=LiftFactorFpHom(fphom,Source(fphom),false,mpcgs);
- RUN_IN_GGMBI:=false;
+ PopOptions();
fp:=Image(fphom);
sp:=Concatenation(sp,mpcgs);
fi;
@@ -1443,10 +1445,10 @@ local ser,hom,s,fphom,sf,sg,sp,fp,d,head,mran,nran,mpcgs,ocr,len,pcgs,
gens:=GeneratorsOfGroup(ocr.complement);
sg:=gens{[1..Length(sg)]};
sp:=gens{[Length(sg)+1..Length(gens)]};
- RUN_IN_GGMBI:=true; # hack to skip Nice treatment
+ PushOptions( rec( Run_In_GGMBI:= true ) ); # hack to skip Nice treatment
fphom:=GroupGeneralMappingByImagesNC(ocr.complement,fp,gens,
GeneratorsOfGroup(fp));
- RUN_IN_GGMBI:=false;
+ PopOptions();
fi;
od;
diff --git a/lib/fldabnum.gi b/lib/fldabnum.gi
index 5902772c5e..cfc60cc6d9 100644
--- a/lib/fldabnum.gi
+++ b/lib/fldabnum.gi
@@ -1918,9 +1918,10 @@ InstallMethod( PreImageElm,
#############################################################################
##
+#M PreImagesElmNC( , ) . . . . . for autom. of ab. number fields
#M PreImagesElm( , ) . . . . . . for autom. of ab. number fields
##
-InstallMethod( PreImagesElm,
+InstallMethod( PreImagesElmNC,
"for ANF automorphism and scalar",
FamRangeEqFamElm,
[ IsFieldHomomorphism and IsANFAutomorphismRep, IsScalar ],
@@ -1929,12 +1930,23 @@ InstallMethod( PreImagesElm,
mod Conductor( Range( aut ) ) ) ];
end );
+InstallMethod( PreImagesElm,
+ "for ANF automorphism and scalar",
+ FamRangeEqFamElm,
+ [ IsFieldHomomorphism and IsANFAutomorphismRep, IsScalar ],
+ function ( aut, elm )
+ if not ( elm in Range(aut) ) then
+ return fail;
+ fi;
+ return PreImagesElmNC( aut, elm );
+ end );
#############################################################################
##
-#M PreImagesSet( , ) . . . . . for autom. of ab. number fields
+#M PreImagesSetNC( , ) . . . . . for autom. of ab. number fields
+#M PreImagesSet( , ) . . . . . . for autom. of ab. number fields
##
-InstallMethod( PreImagesSet,
+InstallMethod( PreImagesSetNC,
"for ANF automorphism and scalar",
CollFamRangeEqFamElms,
[ IsFieldHomomorphism and IsANFAutomorphismRep, IsField ],
@@ -1942,12 +1954,23 @@ InstallMethod( PreImagesSet,
return F;
end );
+InstallMethod( PreImagesSet,
+ "for ANF automorphism and scalar",
+ CollFamRangeEqFamElms,
+ [ IsFieldHomomorphism and IsANFAutomorphismRep, IsField ],
+ function ( aut, F )
+ if not IsSubset( Range(aut), F ) then
+ return fail;
+ fi;
+ return PreImagesSetNC( aut, F );
+ end );
#############################################################################
##
+#M PreImagesRepresentativeNC( , ) for autom. of ab. number fields
#M PreImagesRepresentative( , ) . for autom. of ab. number fields
##
-InstallMethod( PreImagesRepresentative,
+InstallMethod( PreImagesRepresentativeNC,
"for ANF automorphism and scalar",
FamRangeEqFamElm,
[ IsFieldHomomorphism and IsANFAutomorphismRep, IsScalar ],
@@ -1956,6 +1979,16 @@ InstallMethod( PreImagesRepresentative,
mod Conductor( Range( aut ) ) );
end );
+InstallMethod( PreImagesRepresentative,
+ "for ANF automorphism and scalar",
+ FamRangeEqFamElm,
+ [ IsFieldHomomorphism and IsANFAutomorphismRep, IsScalar ],
+ function ( aut, elm )
+ if not ( elm in Range( aut ) ) then
+ return fail;
+ fi;
+ return PreImagesRepresentativeNC( aut, elm );
+ end );
#############################################################################
##
diff --git a/lib/ghom.gi b/lib/ghom.gi
index bc217f1e32..29caa4a36b 100644
--- a/lib/ghom.gi
+++ b/lib/ghom.gi
@@ -253,9 +253,10 @@ end );
#############################################################################
##
+#M PreImagesRepresentativeNC( , ) . . . . . . . . . . via images
#M PreImagesRepresentative( , ) . . . . . . . . . . . via images
-##
-InstallMethod( PreImagesRepresentative, "for PBG-Hom", FamRangeEqFamElm,
+
+InstallMethod( PreImagesRepresentativeNC, "for PBG-Hom", FamRangeEqFamElm,
[ IsPreimagesByAsGroupGeneralMappingByImages,
IsMultiplicativeElementWithInverse ], 0,
function( hom, elm )
@@ -264,8 +265,18 @@ function( hom, elm )
# group
return ImagesRepresentative( RestrictedInverseGeneralMapping( hom ), elm );
else
- return PreImagesRepresentative( AsGroupGeneralMappingByImages( hom ), elm );
+ return PreImagesRepresentativeNC( AsGroupGeneralMappingByImages( hom ), elm );
+ fi;
+end );
+
+InstallMethod( PreImagesRepresentative, "for PBG-Hom", FamRangeEqFamElm,
+ [ IsPreimagesByAsGroupGeneralMappingByImages,
+ IsMultiplicativeElementWithInverse ], 0,
+function( hom, elm )
+ if not ( elm in Range( hom ) ) then
+ return fail;
fi;
+ return PreImagesRepresentativeNC( hom, elm );
end );
InstallAttributeMethodByGroupGeneralMappingByImages( CoKernelOfMultiplicativeGeneralMapping );
@@ -875,9 +886,9 @@ InstallMethod( ImagesRepresentative,
#############################################################################
##
-#M PreImagesRepresentative( , ) . . . . . . . . . . . . for GHBI
+#M PreImagesRepresentativeNC( , ) . . . . . . . . . . . . for GHBI
##
-InstallMethod( PreImagesRepresentative,
+InstallMethod( PreImagesRepresentativeNC,
"for GHBI and mult.-elm.-with-inverse",
FamRangeEqFamElm,
[ IsGroupGeneralMappingByImages,
@@ -1225,9 +1236,9 @@ InstallMethod( ImagesSet,
#############################################################################
##
-#M PreImagesRepresentative( , ) . . . . for conjugator isomorphism
+#M PreImagesRepresentativeNC( , ) . . . . for conjugator isomorphism
##
-InstallMethod( PreImagesRepresentative,
+InstallMethod( PreImagesRepresentativeNC,
"for conjugator isomorphism",
FamRangeEqFamElm,
[ IsConjugatorIsomorphism, IsMultiplicativeElementWithInverse ], 0,
@@ -1238,9 +1249,9 @@ InstallMethod( PreImagesRepresentative,
#############################################################################
##
-#M PreImagesSet( , ) . . . . . . . . . for conjugator isomorphism
+#M PreImagesSetNC( , ) . . . . . . . . . for conjugator isomorphism
##
-InstallMethod( PreImagesSet,
+InstallMethod( PreImagesSetNC,
"for conjugator isomorphism, and group",
CollFamRangeEqFamElms,
[ IsConjugatorIsomorphism, IsGroup ], 0,
diff --git a/lib/ghomfp.gi b/lib/ghomfp.gi
index fcc83630d9..86d7fa5a9f 100644
--- a/lib/ghomfp.gi
+++ b/lib/ghomfp.gi
@@ -441,7 +441,7 @@ local q,r,tg,dtg,pemb,ugens,g,gi,d,o,gens,genims,i,gr,img,l,mapi;
#better: orbit algo
#r:=ShallowCopy(RightTransversal(q,qu));
#Sort(r,function(a,b) return 1^a<1^b;end);
- #r:=List(r,i->PreImagesRepresentative(beta,i));
+ #r:=List(r,i->PreImagesRepresentativeNC(beta,i));
# compute transversal with short words from orbit algorithm on points
o:=[1];
@@ -527,9 +527,10 @@ end);
#############################################################################
##
+#M PreImagesSetNC( , )
#M PreImagesSet( , )
##
-InstallMethod( PreImagesSet, "map from (sub)group of fp group",
+InstallMethod( PreImagesSetNC, "map from (sub)group of fp group",
CollFamRangeEqFamElms,
[ IsFromFpGroupHomomorphism,IsGroup ],0,
function(hom,u)
@@ -624,6 +625,16 @@ local s,gens,t,p,w,c,q,chom,tg,thom,hi,i,lp,max;
return SubgroupOfWholeGroupByQuotientSubgroup(FamilyObj(s),u,Stabilizer(u,1));
end);
+InstallMethod( PreImagesSet, "map from (sub)group of fp group",
+ CollFamRangeEqFamElms,
+ [ IsFromFpGroupHomomorphism,IsGroup ],0,
+function(hom,u)
+ if not IsSubset( Range(hom), u ) then
+ return fail;
+ fi;
+ return PreImagesSetNC(hom,u);
+end);
+
#############################################################################
##
@@ -718,9 +729,10 @@ end);
#############################################################################
##
+#M PreImagesRepresentativeNC
#M PreImagesRepresentative
##
-InstallMethod( PreImagesRepresentative,
+InstallMethod( PreImagesRepresentativeNC,
"hom. to standard generators of fp group, using 'MappedWord'",
FamRangeEqFamElm,
[IsToFpGroupHomomorphismByImages,IsMultiplicativeElementWithInverse],
@@ -747,6 +759,19 @@ local mapi;
return mapi;
end);
+InstallMethod( PreImagesRepresentative,
+ "hom. to standard generators of fp group, using 'MappedWord'",
+ FamRangeEqFamElm,
+ [IsToFpGroupHomomorphismByImages,IsMultiplicativeElementWithInverse],
+ 1,
+function(hom,elm)
+ if not (elm in Range(hom)) then
+ return fail;
+ fi;
+ return PreImagesRepresentativeNC(hom,elm);
+end);
+
+
#############################################################################
##
## methods to construct homomorphisms to fp groups
@@ -1282,7 +1307,7 @@ local v,aiu,aiv,G,primes,irrel,ma,mau,a,k,gens,imgs,q,dec,deco,piv,co;
fi;
gens:=SmallGeneratingSet(a);
- imgs:=List(gens,x->Image(mau,Image(hom,PreImagesRepresentative(ma,x))));
+ imgs:=List(gens,x->Image(mau,Image(hom,PreImagesRepresentativeNC(ma,x))));
q:=GroupHomomorphismByImages(a,Image(mau),gens,imgs);
k:=KernelOfMultiplicativeGeneralMapping(q);
@@ -1293,7 +1318,7 @@ local v,aiu,aiv,G,primes,irrel,ma,mau,a,k,gens,imgs,q,dec,deco,piv,co;
dec:=EpimorphismFromFreeGroup(Group(gens));
deco:=function(x)
local i;
- x:=ExponentSums(PreImagesRepresentative(dec,x));
+ x:=ExponentSums(PreImagesRepresentativeNC(dec,x));
for i in [1..Length(aiv)] do
x[i]:=x[i] mod aiv[i];
od;
@@ -1330,7 +1355,7 @@ local hom,pcgs,impcgs;
impcgs:=FamilyPcgs(Image(hom,M));
pcgs:=PcgsByPcSequenceCons(IsPcgsDefaultRep,IsModuloPcgsFpGroupRep,
ElementsFamily(FamilyObj(M)),
- List(impcgs,i->PreImagesRepresentative(hom,i)),
+ List(impcgs,i->PreImagesRepresentativeNC(hom,i)),
[]
);
pcgs!.hom:=hom;
diff --git a/lib/ghompcgs.gi b/lib/ghompcgs.gi
index f17db8b36c..984f80f3f3 100644
--- a/lib/ghompcgs.gi
+++ b/lib/ghompcgs.gi
@@ -503,9 +503,10 @@ end);
#############################################################################
##
+#M PreImagesRepresentativeNC( , ) . . . . . . . . . . via images
#M PreImagesRepresentative( , ) . . . . . . . . . . . via images
##
-InstallMethod( PreImagesRepresentative, "method for pcgs hom",
+InstallMethod( PreImagesRepresentativeNC, "method for pcgs hom",
FamRangeEqFamElm,
[ IsToPcGroupHomomorphismByImages,IsMultiplicativeElementWithInverse ], 0,
function( hom, elm )
@@ -530,6 +531,16 @@ function( hom, elm )
return pre;
end);
+InstallMethod( PreImagesRepresentative, "method for pcgs hom",
+ FamRangeEqFamElm,
+ [ IsToPcGroupHomomorphismByImages,IsMultiplicativeElementWithInverse ], 0,
+function( hom, elm )
+ if not ( elm in Range( hom ) ) then
+ return fail;
+ fi;
+ return PreImagesRepresentativeNC( hom, elm );
+end );
+
#############################################################################
##
#M NaturalHomomorphismByNormalSubgroup( , ) . . . . . . for pc groups
@@ -627,9 +638,9 @@ end );
#############################################################################
##
-#M PreImagesRepresentative( , ) . . . . . . . . . . via depth map
+#M PreImagesRepresentativeNC( , ) . . . . . . . . . via depth map
##
-InstallMethod( PreImagesRepresentative, FamRangeEqFamElm,
+InstallMethod( PreImagesRepresentativeNC, FamRangeEqFamElm,
[ IsPcgsToPcgsHomomorphism,IsMultiplicativeElementWithInverse ], 0,
function( hom, elm )
local exp;
diff --git a/lib/ghomperm.gi b/lib/ghomperm.gi
index 2f103a6a37..8b5c6a79dd 100644
--- a/lib/ghomperm.gi
+++ b/lib/ghomperm.gi
@@ -11,9 +11,9 @@
#############################################################################
##
-#M PreImagesSet( , ) . for s.p. gen. mapping resp. mult. & inv.
+#M PreImagesSetNC( , ) . for s.p. gen. mapping resp. mult. & inv.
##
-InstallMethod( PreImagesSet,
+InstallMethod( PreImagesSetNC,
"method for permgroup homs",
CollFamRangeEqFamElms,
[ IsPermGroupHomomorphism, IsGroup ],
@@ -22,7 +22,7 @@ local genpreimages, pre,kg,sz,ol,orb,pos,dom,one;
genpreimages:=GeneratorsOfMagmaWithInverses( elms );
genpreimages:= List(genpreimages,
- gen -> PreImagesRepresentative( map, gen ) );
+ gen -> PreImagesRepresentativeNC( map, gen ) );
if fail in genpreimages then
TryNextMethod();
fi;
@@ -1152,7 +1152,7 @@ local r, fgens, gens, kg;
fi;
fgens:=ShallowCopy(GeneratorsOfGroup(r));
gens:=List(fgens,
- i->PreImagesRepresentative(hom2,PreImagesRepresentative(hom1,i)));
+ i->PreImagesRepresentativeNC(hom2,PreImagesRepresentativeNC(hom1,i)));
kg:=GeneratorsOfGroup(KernelOfMultiplicativeGeneralMapping(hom2));
Append(gens,kg);
Append(fgens,List(kg,i->One(r)));
@@ -1162,15 +1162,26 @@ end);
#############################################################################
##
+#M PreImagesRepresentativeNC( , ) . . . . . for perm group range
#M PreImagesRepresentative( , ) . . . . . . for perm group range
##
-InstallMethod( PreImagesRepresentative, FamRangeEqFamElm,
+InstallMethod( PreImagesRepresentativeNC, FamRangeEqFamElm,
[ IsToPermGroupGeneralMappingByImages,
IsMultiplicativeElementWithInverse ], 0,
function( hom, elm )
return ImagesRepresentative( RestrictedInverseGeneralMapping( hom ), elm );
end );
+InstallMethod( PreImagesRepresentative, FamRangeEqFamElm,
+ [ IsToPermGroupGeneralMappingByImages,
+ IsMultiplicativeElementWithInverse ], 0,
+ function( hom, elm )
+ if not ( elm in Range( hom ) ) then
+ return fail;
+ fi;
+ return PreImagesRepresentativeNC( hom, elm );
+end );
+
#############################################################################
##
#F StabChainPermGroupToPermGroupGeneralMappingByImages( ) . . . local
@@ -1562,9 +1573,9 @@ InstallMethod( ImagesSource,"constituent homomorphism",true,
#############################################################################
##
-#M PreImagesRepresentative( , )
+#M PreImagesRepresentativeNC( , )
##
-InstallMethod( PreImagesRepresentative,"constituent homomorphism",
+InstallMethod( PreImagesRepresentativeNC,"constituent homomorphism",
FamRangeEqFamElm,[IsConstituentHomomorphism,IsPerm], 0,
function( hom, elm )
local D,DP;
@@ -1579,9 +1590,9 @@ end);
#############################################################################
##
-#M PreImagesSet( , ) . . . . . . . . . . . . . . . . for const hom
+#M PreImagesSetNC( , ) . . . . . . . . . . . . . . . for const hom
##
-InstallMethod( PreImagesSet, "constituent homomorphism",CollFamRangeEqFamElms,
+InstallMethod( PreImagesSetNC, "constituent homomorphism",CollFamRangeEqFamElms,
[ IsConstituentHomomorphism, IsPermGroup ], 0,
function( hom, I )
local H, # preimage of , result
@@ -1594,7 +1605,7 @@ InstallMethod( PreImagesSet, "constituent homomorphism",CollFamRangeEqFamElms,
# create the preimage group
H := EmptyStabChain( [ ], One( Source( hom ) ) );
S := ConjugateStabChain( StabChainMutable( I ), H, x ->
- PreImagesRepresentative( hom, x ), hom!.conperm ^ -1 );
+ PreImagesRepresentativeNC( hom, x ), hom!.conperm ^ -1 );
T := H;
while IsBound( T.stabilizer ) do
AddGeneratorsExtendSchreierTree( T, GeneratorsOfGroup( K ) );
@@ -1817,9 +1828,9 @@ end );
#############################################################################
##
-#M PreImagesRepresentative( , ) . . . . . . . . . for blocks hom
+#M PreImagesRepresentativeNC( , ) . . . . . . . . for blocks hom
##
-InstallMethod( PreImagesRepresentative, "blocks homomorphism",
+InstallMethod( PreImagesRepresentativeNC, "blocks homomorphism",
FamRangeEqFamElm,
[ IsBlocksHomomorphism, IsMultiplicativeElementWithInverse ], 0,
function( hom, elm )
@@ -1869,9 +1880,9 @@ end) ;
#############################################################################
##
-#M PreImagesSet( , ) . . . . . . . . . . . . . . . for blocks hom
+#M PreImagesSetNC( , ) . . . . . . . . . . . . . . for blocks hom
##
-InstallMethod( PreImagesSet, CollFamRangeEqFamElms,
+InstallMethod( PreImagesSetNC, CollFamRangeEqFamElms,
[ IsBlocksHomomorphism, IsPermGroup ], 0,
function( hom, I )
local H; # preimage of under , result
@@ -1905,7 +1916,7 @@ InstallGlobalFunction( PreImageSetStabBlocksHomomorphism, function( hom, I )
H := PreImageSetStabBlocksHomomorphism( hom, I.stabilizer );
ChangeStabChain( H, [ pnt ], false );
for gen in I.generators do
- pre := PreImagesRepresentative( hom, gen );
+ pre := PreImagesRepresentativeNC( hom, gen );
if not IsBound( H.translabels[ pnt ^ pre ] ) then
AddGeneratorsExtendSchreierTree( H, [ pre ] );
fi;
diff --git a/lib/gpfpiso.gi b/lib/gpfpiso.gi
index 202d9419a7..8095dd5be1 100644
--- a/lib/gpfpiso.gi
+++ b/lib/gpfpiso.gi
@@ -91,7 +91,7 @@ local l,iso,fp,stbc,gens;
fp:=IsomorphismFpGroup(l);
iso:=GroupHomomorphismByImagesNC(G,Range(fp),
List(MappingGeneratorsImages(fp)[1],
- i->PreImagesRepresentative(iso,i)),
+ i->PreImagesRepresentativeNC(iso,i)),
MappingGeneratorsImages(fp)[2]);
SetIsBijective(iso,true);
return iso;
@@ -171,8 +171,8 @@ function( G, str )
IsNaturalAlternatingGroup(H);
new:=IsomorphismFpGroup(H,"@");
gensH:=List(GeneratorsOfGroup(Image(new)),
- i->PreImagesRepresentative(new,i));
- preiH := List( gensH, x -> PreImagesRepresentative( hom, x ) );
+ i->PreImagesRepresentativeNC(new,i));
+ preiH := List( gensH, x -> PreImagesRepresentativeNC( hom, x ) );
c := Length( gensH );
@@ -190,7 +190,7 @@ function( G, str )
w := MappedWord( rel, gensT, gensE{[1..c]} );
t := MappedWord( rel, gensT, imgsE{[1..c]} );
if not t = One( G ) then
- t := PreImagesRepresentative( free, t );
+ t := PreImagesRepresentativeNC( free, t );
t := MappedWord( t, gensF, gensE{[c+1..n+c]} );
else
t := One( E );
@@ -204,7 +204,7 @@ function( G, str )
w := Comm( gensE[c+j], gensE[i] );
t := Comm( imgsE[c+j], imgsE[i] );
if not t = One( G ) then
- t := PreImagesRepresentative( free, t );
+ t := PreImagesRepresentativeNC( free, t );
t := MappedWord( t, gensF, gensE{[c+1..n+c]} );
else
t := One( E );
@@ -293,7 +293,7 @@ function(g,str,N)
gens:=Union(gens,Union(List(ser,SmallGeneratingSet)));
fi;
if f<>g then
- gens:=List(gens,x->PreImagesRepresentative(hom,x));
+ gens:=List(gens,x->PreImagesRepresentativeNC(hom,x));
ser:=List(ser,x->PreImage(hom,x));
fi;
# change generators to make split
@@ -397,7 +397,8 @@ function(g,str,N)
fgens:=GeneratorsOfGroup(f);
auts:=List(GeneratorsOfGroup(g),i->
GroupHomomorphismByImagesNC(f,f,fgens,
- List(fgens,j->Image(hom,PreImagesRepresentative(hom,j)^i)):noassert));
+ List(fgens,
+ j->Image(hom,PreImagesRepresentativeNC(hom,j)^i)):noassert));
for j in auts do
SetIsBijective(j,true);
od;
@@ -426,7 +427,7 @@ function(g,str,N)
else
a:=IsomorphismFpGroup(sf:noassert);
fi;
- ad:=List(GeneratorsOfGroup(Range(a)),i->PreImagesRepresentative(a,i));
+ ad:=List(GeneratorsOfGroup(Range(a)),i->PreImagesRepresentativeNC(a,i));
lad:=Length(ad);
n:=Length(orb);
@@ -461,7 +462,7 @@ function(g,str,N)
fp:=fg/rels;
a:=GroupHomomorphismByImagesNC(f,fp,fgens,GeneratorsOfGroup(fp):noassert);
fi;
- Append(gens,List(fgens,i->PreImagesRepresentative(hom,i)));
+ Append(gens,List(fgens,i->PreImagesRepresentativeNC(hom,i)));
# here we really want a composed homomorphism, to avoid extra work for
# a new stabilizer chain
@@ -640,7 +641,7 @@ local fpq, qgens, qreps, fpqg, rels, pcgs, p, f, qimg, idx, nimg, decomp,
ngen, fp, hom2, di, source, dih, dec, i, j;
fpq:=Range(hom);
qgens:=GeneratorsOfGroup(fpq);
- qreps:=List(qgens,i->PreImagesRepresentative(hom,i));
+ qreps:=List(qgens,i->PreImagesRepresentativeNC(hom,i));
fpqg:=FreeGeneratorsOfFpGroup(fpq);
rels:=[];
if IsModuloPcgs(mnsf) then
@@ -694,7 +695,7 @@ local fpq, qgens, qreps, fpqg, rels, pcgs, p, f, qimg, idx, nimg, decomp,
ngen:=FreeGeneratorsOfFpGroup(p);
# This is not really a pcgs, but treated as layer generators the same
# way, thus use the same variable name
- pcgs:=List(GeneratorsOfGroup(p),i->PreImagesRepresentative(mnsf,i));
+ pcgs:=List(GeneratorsOfGroup(p),i->PreImagesRepresentativeNC(mnsf,i));
f:=FreeGroup(Length(fpqg)+Length(pcgs));
qimg:=GeneratorsOfGroup(f){[1..Length(fpqg)]};
idx:=[Length(fpqg)+1..Length(fpqg)+Length(pcgs)];
@@ -966,7 +967,7 @@ function( G, series, str )
gensH := GeneratorsOfGroup( H );
gensH := Filtered( gensH, x -> x <> One(H) );
- preiH := List( gensH, x -> PreImagesRepresentative( hom, x ) );
+ preiH := List( gensH, x -> PreImagesRepresentativeNC( hom, x ) );
c := Length( gensH );
# compute presentation of H
@@ -989,7 +990,7 @@ function( G, series, str )
w := MappedWord( rel, gensT, gensE{[1..c]} );
t := MappedWord( rel, gensT, imgsE{[1..c]} );
if not t = One( G ) then
- t := PreImagesRepresentative( free, t );
+ t := PreImagesRepresentativeNC( free, t );
t := MappedWord( t, gensF, gensE{[c+1..n+c]} );
else
t := One( E );
@@ -1003,7 +1004,7 @@ function( G, series, str )
w := Comm( gensE[c+j], gensE[i] );
t := Comm( imgsE[c+j], imgsE[i] );
if not t = One( G ) then
- t := PreImagesRepresentative( free, t );
+ t := PreImagesRepresentativeNC( free, t );
t := MappedWord( t, gensF, gensE{[c+1..n+c]} );
else
t := One( E );
@@ -1228,8 +1229,8 @@ local iso,fp,dec,homs,mos,i,j,ffp,imo,m,k,gens,fm,mgens,rules,
for r in Rules(k) do
left:=MappedWord(r[1],FreeGeneratorsOfFpMonoid(m),monreps);
right:=MappedWord(r[2],FreeGeneratorsOfFpMonoid(m),monreps);
- diff:=LeftQuotient(PreImagesRepresentative(iso,right),
- PreImagesRepresentative(iso,left));
+ diff:=LeftQuotient(PreImagesRepresentativeNC(iso,right),
+ PreImagesRepresentativeNC(iso,left));
diff:=ImagesRepresentative(iso,diff);
left:=MappedWord(r[1],FreeGeneratorsOfFpMonoid(m),monreal);
@@ -1248,7 +1249,7 @@ local iso,fp,dec,homs,mos,i,j,ffp,imo,m,k,gens,fm,mgens,rules,
if reduce(mgens[k])=mgens[k] then
right:=fmgens[j]^-1*fmgens[k]*fmgens[j];
#collect
- right:=ImagesRepresentative(iso,PreImagesRepresentative(iso,right));
+ right:=ImagesRepresentative(iso,PreImagesRepresentativeNC(iso,right));
right:=Product(List(LetterRepAssocWord(UnderlyingElement(right)),
x->mgens[Position(nums,x)]));
right:=reduce(mgens[j]*right);
@@ -1320,7 +1321,7 @@ local pcgs,iso,fp,i,j,gens,numi,ord,fm,fam,mword,k,r,addrule,a,e,m;
pcgs:=Pcgs(G);
iso:=IsomorphismFpGroup(G);
fp:=Range(iso);
- if List(GeneratorsOfGroup(fp),x->PreImagesRepresentative(iso,x))<>pcgs then
+ if List(GeneratorsOfGroup(fp),x->PreImagesRepresentativeNC(iso,x))<>pcgs then
Error("pcgs");
fi;
gens:=[];
@@ -1520,7 +1521,7 @@ local iso,n,fn,sz,bigcount,tryweyl;
iso:=IsomorphismGroups(G,P);
if iso<>fail then
P:=List(GeneratorsOfGroup(H),
- x->PreImagesRepresentative(iso,ImagesRepresentative(isp,x)));
+ x->PreImagesRepresentativeNC(iso,ImagesRepresentative(isp,x)));
iso:=GroupHomomorphismByImagesNC(G,H,P,GeneratorsOfGroup(H));
fi;
return iso;
@@ -1728,13 +1729,13 @@ local isob,isos,iso,gens,a,rels,l,i,j,bgens,cb,cs,b,f,k,w,monoid,
# force going to pc group, as this will give better ordering
isob:=GroupHomomorphismByFunction(borel,Range(cb.fphom),
x->ImagesRepresentative(cb.fphom,ImagesRepresentative(pciso,x)),
- x->PreImagesRepresentative(pciso,PreImagesRepresentative(cb.fphom,x)));
+ x->PreImagesRepresentativeNC(pciso,PreImagesRepresentativeNC(cb.fphom,x)));
b:=Range(isob);
wgens:=GeneratorsOfGroup(weyl);
- bgens:=List(GeneratorsOfGroup(b),x->PreImagesRepresentative(isob,x));
+ bgens:=List(GeneratorsOfGroup(b),x->PreImagesRepresentativeNC(isob,x));
if newstyle and bgens<>GeneratorsOfGroup(borel) then Error("gens");fi;
bpairs:=Concatenation(List(bgens,x->[x,x^-1]));
@@ -1879,7 +1880,7 @@ local isob,isos,iso,gens,a,rels,l,i,j,bgens,cb,cs,b,f,k,w,monoid,
x:=UnderlyingElement(ImagesRepresentative(cb.monhom,x));
x:=reduce(x,RelationsOfFpMonoid(monoid),mdag,fail);
x:=ElementOfFpMonoid(FamilyObj(One(monoid)),x);
- return PreImagesRepresentative(cb.monhom,x);
+ return PreImagesRepresentativeNC(cb.monhom,x);
end;
mdag:=EmptyKBDAG(Union(List(FreeGeneratorsOfFpMonoid(monoid),
@@ -1924,7 +1925,7 @@ local isob,isos,iso,gens,a,rels,l,i,j,bgens,cb,cs,b,f,k,w,monoid,
x:=UnderlyingElement(ImagesRepresentative(cs.monhom,x));
x:=reduce(x,RelationsOfFpMonoid(Range(cs.monhom)),wdag,fail);
x:=ElementOfFpMonoid(FamilyObj(One(Range(cs.monhom))),x);
- return PreImagesRepresentative(cs.monhom,x);
+ return PreImagesRepresentativeNC(cs.monhom,x);
end;
wdag:=EmptyKBDAG(Union(List(FreeGeneratorsOfFpMonoid(Range(cs.monhom)),
@@ -1966,7 +1967,7 @@ local isob,isos,iso,gens,a,rels,l,i,j,bgens,cb,cs,b,f,k,w,monoid,
a:=Group(SmallGeneratingSet(group)); # so nothing stores
csetperm:=List(GeneratorsOfGroup(a),x->Permutation(x,rt,OnRight));
iso:=EpimorphismFromFreeGroup(a);
- csetperm:=List(bgens,x->MappedWord(PreImagesRepresentative(iso,x),
+ csetperm:=List(bgens,x->MappedWord(PreImagesRepresentativeNC(iso,x),
MappingGeneratorsImages(iso)[1],csetperm));
act:=Group(csetperm,());
@@ -2014,7 +2015,7 @@ local isob,isos,iso,gens,a,rels,l,i,j,bgens,cb,cs,b,f,k,w,monoid,
a:=PositionCanonical(rt,elm);
b:=rti[a];
rep:=RepresentativeAction(Image(bhom),a,dcnums[b][1]);
- rep:=PreImagesRepresentative(bhom,rep);
+ rep:=PreImagesRepresentativeNC(bhom,rep);
if single then
a:=[CanonicalRightCosetElement(ac[1],rt[dcnums[b][1]]),rep];
else
@@ -2074,9 +2075,8 @@ local isob,isos,iso,gens,a,rels,l,i,j,bgens,cb,cs,b,f,k,w,monoid,
# a:=Group(SmallGeneratingSet(group)); # so nothing stores
# csetperm:=List(GeneratorsOfGroup(a),x->Permutation(x,rt,OnRight));
# iso:=EpimorphismFromFreeGroup(a);
-# csetperm:=List(bgens,x->MappedWord(PreImagesRepresentative(iso,x),MappingGeneratorsImages(iso)[1],csetperm));
-# act:=Group(csetperm,());
-#
+# csetperm:=List(bgens,x->MappedWord(PreImagesRepresentativeNC(iso,x),
+# MappingGeneratorsImages(iso)[1],csetperm)); act:=Group(csetperm,());
# bhom:=GroupHomomorphismByImagesNC(borel,act,bgens,csetperm);
# #Assert(0,bhom<>fail);
#
@@ -2119,7 +2119,7 @@ local isob,isos,iso,gens,a,rels,l,i,j,bgens,cb,cs,b,f,k,w,monoid,
# pos:=rti[PositionCanonical(rt,elm)];
# #rep:=RepresentativeAction(borel,PositionCanonical(rt,elm),
# # PositionCanonical(rt,dcreps[pos]),bgens,csetperm,OnPoints);
-# rep:=PreImagesRepresentative(bhom,
+# rep:=PreImagesRepresentativeNC(bhom,
# RepresentativeAction(Range(bhom),PositionCanonical(rt,elm),
# PositionCanonical(rt,dcreps[pos])));
# rep:=[elm*rep/dcreps[pos],dcreps[pos],rep^-1];
@@ -2441,7 +2441,7 @@ if rule[1]=rule[2] then return;fi;
else
# BN-style reductions
- pcgs:=List(GeneratorsOfGroup(b),x->PreImagesRepresentative(isob,x));
+ pcgs:=List(GeneratorsOfGroup(b),x->PreImagesRepresentativeNC(isob,x));
# remove powers
pcgs:=pcgs{
Filtered([1..Length(pcgs)],i->not ForAny([1..i-1],
@@ -2455,7 +2455,7 @@ if rule[1]=rule[2] then return;fi;
# which elements b*i can we write as i*\tilde b. Then b^i=\tilde b, that
# is b\in B\cvap B^(i^-1)
- pri:=PreImagesRepresentative(isos,i);
+ pri:=PreImagesRepresentativeNC(isos,i);
stb:=Intersection(borel,borel^(pri^-1));
Info(InfoFpGroup,2,i," ",Size(stb));
@@ -2511,14 +2511,14 @@ if rule[1]=rule[2] then return;fi;
Info(InfoFpGroup,3,"borelrun ",Position(wo,i)," of ",Length(wo));
# rewrite i*b*j as \tilde b*k*\hat b.
- pri:=PreImagesRepresentative(isos,i);
+ pri:=PreImagesRepresentativeNC(isos,i);
stb:=Intersection(borel^pri,borel);
for j in wo do
Info(InfoFpGroup,2,"DC:",i,", ",j," from ",Length(rels));
for k in borelelm do #RightTransversal(borel,stb) do
- a:=PreImagesRepresentative(isos,i)*k*
- PreImagesRepresentative(isos,j);
+ a:=PreImagesRepresentativeNC(isos,i)*k*
+ PreImagesRepresentativeNC(isos,j);
a:=decomp(a);
a:=[nofob(ImagesRepresentative(isob,a[1])),
nofow(ImagesRepresentative(isos,a[2])),
@@ -2684,7 +2684,7 @@ end);
# if List(mg,x->LetterRepAssocWord(UnderlyingElement(x)))<>
# List([1..Length(mg)],x->[x]) then Error("gens!"); fi;
# pre:=List(mg,x->LetterRepAssocWord(UnderlyingElement(
-# PreImagesRepresentative(miso,x))));
+# PreImagesRepresentativeNC(miso,x))));
# if ForAny(pre,x->Length(x)<>1) then Error("double");fi;
# Add(l,Concatenation(pre));
# if IsBound(m!.rewritingSystem) then
@@ -2896,7 +2896,7 @@ local d,f,group,act,g,sy,b,c,borel,weyl,a,i,iso,ucs,gens,gl;
fi;
c:=c[1];
a:=SubgroupNC(group,List(GeneratorsOfGroup(weyl),
- x->PreImagesRepresentative(c,x)));
+ x->PreImagesRepresentativeNC(c,x)));
Size(a);
a!.epiweyl:=weyl;
weyl:=a;
diff --git a/lib/gpprmsya.gi b/lib/gpprmsya.gi
index a88508a2bb..d0af65692e 100644
--- a/lib/gpprmsya.gi
+++ b/lib/gpprmsya.gi
@@ -1265,7 +1265,7 @@ syll, act, typ, sel, bas, wdom, comp, lperm, other, away, i, j,b0,opg,bp;
w:=AutomorphismGroup(b);
opg:=NaturalHomomorphismByNormalSubgroupNC(w,
InnerAutomorphismsAutomorphismGroup(w));
- ll:=List(AsSSortedList(Image(opg)),x->PreImagesRepresentative(opg,x));
+ ll:=List(AsSSortedList(Image(opg)),x->PreImagesRepresentativeNC(opg,x));
ll:=Filtered(ll,IsConjugatorAutomorphism);
ll:=List(ll,ConjugatorInnerAutomorphism);
pg:=b;
diff --git a/lib/gprd.gi b/lib/gprd.gi
index e32bf13af7..49b091d983 100644
--- a/lib/gprd.gi
+++ b/lib/gprd.gi
@@ -715,7 +715,7 @@ InstallGlobalFunction(InnerSubdirectProducts2,function( D, U, V )
# and obtain double coset reps
reps := List( DoubleCosets( P, autU, autV ), Representative );
- reps := List( reps, x -> PreImagesRepresentative( gamma, x ) );
+ reps := List( reps, x -> PreImagesRepresentativeNC( gamma, x ) );
# loop over automorphisms
for rep in reps do
@@ -724,9 +724,9 @@ InstallGlobalFunction(InnerSubdirectProducts2,function( D, U, V )
gens := Concatenation( GeneratorsOfGroup( N ),
GeneratorsOfGroup( M ) );
for r in GeneratorsOfGroup( UN ) do
- g := PreImagesRepresentative( pair[1], r );
+ g := PreImagesRepresentativeNC( pair[1], r );
h := Image( iso, Image( rep, r ) );
- h := PreImagesRepresentative( pair[2], h );
+ h := PreImagesRepresentativeNC( pair[2], h );
Add( gens, g * h );
od;
S := SubgroupNC( D, gens );
@@ -1094,7 +1094,7 @@ local info,map,U,mapfun,P;
function(elm)
elm:=elm![n];
if n>info.degI then
- elm:=PreImagesRepresentative(info.alpha,elm);
+ elm:=PreImagesRepresentativeNC(info.alpha,elm);
fi;
return elm;
end);
@@ -1118,7 +1118,7 @@ local info,map,np;
map:=GroupHomomorphismByFunction(G,info.groups[2],
function(elm)
- return PreImagesRepresentative(info.alpha,elm![np]);
+ return PreImagesRepresentativeNC(info.alpha,elm![np]);
end,
false, # not bijective
function(elm)
@@ -1179,7 +1179,7 @@ local giso,niso,P,gens,a,Go,No,i;
N:=Image(niso,N);
gens:=[];
for i in GeneratorsOfGroup(G) do
- i:=Image(aut,PreImagesRepresentative(giso,i));
+ i:=Image(aut,PreImagesRepresentativeNC(giso,i));
i:=InducedAutomorphism(niso,i);
Add(gens,i);
od;
@@ -1220,9 +1220,9 @@ local Go,No,giso,niso,FG,GP,FN,NP,F,GI,NI,rels,i,j,P;
N:=Image(niso,N);
FG:=FreeGeneratorsOfFpGroup(G);
- GP:=List(GeneratorsOfGroup(G),x->PreImagesRepresentative(giso,x));
+ GP:=List(GeneratorsOfGroup(G),x->PreImagesRepresentativeNC(giso,x));
FN:=FreeGeneratorsOfFpGroup(N);
- NP:=List(GeneratorsOfGroup(N),x->PreImagesRepresentative(niso,x));
+ NP:=List(GeneratorsOfGroup(N),x->PreImagesRepresentativeNC(niso,x));
F:=FreeGroup(List(Concatenation(FG,FN),String));
GI:=GeneratorsOfGroup(F){[1..Length(FG)]};
diff --git a/lib/gprdmat.gi b/lib/gprdmat.gi
index 2480d861d1..d73b63e568 100644
--- a/lib/gprdmat.gi
+++ b/lib/gprdmat.gi
@@ -143,9 +143,10 @@ end);
#############################################################################
##
-#M PreImagesRepresentative(,) . . . . . . . . . . . of embedding
+#M PreImagesRepresentativeNC(,) . . . . . . . . . . . of embedding
+#M PreImagesRepresentative(,) . . . . . . . . . . . . of embedding
##
-InstallMethod(PreImagesRepresentative,"matrix direct product embedding",
+InstallMethod(PreImagesRepresentativeNC,"matrix direct product embedding",
FamRangeEqFamElm,
[ IsEmbeddingDirectProductMatrixGroup,
IsMultiplicativeElementWithInverse ],
@@ -162,6 +163,17 @@ local info,a,b;
fi;
end);
+InstallMethod(PreImagesRepresentative,"matrix direct product embedding",
+ FamRangeEqFamElm,
+ [ IsEmbeddingDirectProductMatrixGroup,
+ IsMultiplicativeElementWithInverse ],
+function(emb,g)
+ if not (g in Range(emb)) then
+ return fail;
+ fi;
+ return PreImagesRepresentativeNC(emb,g);
+end);
+
#############################################################################
##
#R IsProjectionDirectProductMatrixGroup() projection onto direct factor
@@ -206,9 +218,10 @@ end);
#############################################################################
##
-#M PreImagesRepresentative(,) . . . . . . . . . . . of projection
+#M PreImagesRepresentativeNC(,) . . . . . . . . . . . of projection
+#M PreImagesRepresentative(,) . . . . . . . . . . . . of projection
##
-InstallMethod(PreImagesRepresentative,"matrix direct product projection",
+InstallMethod(PreImagesRepresentativeNC,"matrix direct product projection",
FamRangeEqFamElm,
[ IsProjectionDirectProductMatrixGroup,
IsMultiplicativeElementWithInverse ],0,
@@ -220,6 +233,17 @@ local info,a;
return ImmutableMatrix(info.field,a);
end);
+InstallMethod(PreImagesRepresentative,"matrix direct product projection",
+ FamRangeEqFamElm,
+ [ IsProjectionDirectProductMatrixGroup,
+ IsMultiplicativeElementWithInverse ],0,
+function(prj,m)
+ if not (m in Range(prj)) then
+ return fail;
+ fi;
+ return PreImagesRepresentativeNC(prj,m);
+end);
+
#############################################################################
##
#M KernelOfMultiplicativeGeneralMapping() . . . . . . . of projection
@@ -382,9 +406,10 @@ end);
#############################################################################
##
-#M PreImagesRepresentative( , ) . . . . . . . . . . . of embedding
+#M PreImagesRepresentativeNC( , ) . . . . . . . . . . of embedding
+#M PreImagesRepresentative( , ) . . . . . . . . . . . of embedding
##
-InstallMethod( PreImagesRepresentative,
+InstallMethod( PreImagesRepresentativeNC,
"imprim matrix wreath product embedding", FamRangeEqFamElm,
[ IsEmbeddingImprimitiveWreathProductMatrixGroup,
IsMultiplicativeElementWithInverse ], 0,
@@ -401,6 +426,16 @@ local info,a,b;
fi;
end);
+InstallMethod( PreImagesRepresentative,
+ "imprim matrix wreath product embedding", FamRangeEqFamElm,
+ [ IsEmbeddingImprimitiveWreathProductMatrixGroup,
+ IsMultiplicativeElementWithInverse ], 0,
+function( emb, g )
+ if not (g in Range(emb)) then
+ return fail;
+ fi;
+ return PreImagesRepresentativeNC(emb,g);
+end);
#############################################################################
##
diff --git a/lib/gprdpc.gi b/lib/gprdpc.gi
index 6994897c39..a17e46436a 100644
--- a/lib/gprdpc.gi
+++ b/lib/gprdpc.gi
@@ -421,7 +421,7 @@ local pg,ph,kg,kh,ig,ih,mg,mh,S,info;
ig:=InducedPcgs(pg,kg);
ih:=InducedPcgs(ph,kh);
mg:=pg mod ig;
- mh:=List(mg,i->PreImagesRepresentative(hh,Image(gh,i)));
+ mh:=List(mg,i->PreImagesRepresentativeNC(hh,Image(gh,i)));
pg:=Concatenation(mg,ig,List(ih,i->One(G)));
ph:=Concatenation(mh,List(ig,i->One(H)),ih);
S:=SubdirProdPcGroups(G,pg,H,ph);
diff --git a/lib/gprdperm.gi b/lib/gprdperm.gi
index 327f812adc..75583f7a0d 100644
--- a/lib/gprdperm.gi
+++ b/lib/gprdperm.gi
@@ -169,9 +169,10 @@ end );
#############################################################################
##
+#M PreImagesRepresentativeNC( , ) . . . . . . . . . . of embedding
#M PreImagesRepresentative( , ) . . . . . . . . . . . of embedding
##
-InstallMethod( PreImagesRepresentative, "perm direct product embedding",
+InstallMethod( PreImagesRepresentativeNC, "perm direct product embedding",
FamRangeEqFamElm,
[ IsEmbeddingDirectProductPermGroup,
IsMultiplicativeElementWithInverse ],
@@ -191,6 +192,17 @@ InstallMethod( PreImagesRepresentative, "perm direct product embedding",
fi;
end );
+InstallMethod( PreImagesRepresentative, "perm direct product embedding",
+ FamRangeEqFamElm,
+ [ IsEmbeddingDirectProductPermGroup,
+ IsMultiplicativeElementWithInverse ],
+ function( emb, g )
+ if not ( g in Range( emb ) ) then
+ return fail;
+ fi;
+ return PreImagesRepresentativeNC( emb, g );
+end );
+
#############################################################################
##
#M ImagesSource( ) . . . . . . . . . . . . . . . . . . . of embedding
@@ -292,9 +304,10 @@ end );
#############################################################################
##
+#M PreImagesRepresentativeNC( , ) . . . . . . . . . . of projection
#M PreImagesRepresentative( , ) . . . . . . . . . . . of projection
##
-InstallMethod( PreImagesRepresentative,"perm direct product projection",
+InstallMethod( PreImagesRepresentativeNC,"perm direct product projection",
FamRangeEqFamElm,
[ IsProjectionDirectProductPermGroup,
IsMultiplicativeElementWithInverse ], 0,
@@ -302,6 +315,17 @@ InstallMethod( PreImagesRepresentative,"perm direct product projection",
return g ^ DirectProductInfo( Source( prj ) ).perms[ prj!.component ];
end );
+InstallMethod( PreImagesRepresentative,"perm direct product projection",
+ FamRangeEqFamElm,
+ [ IsProjectionDirectProductPermGroup,
+ IsMultiplicativeElementWithInverse ], 0,
+ function( prj, g )
+ if not ( g in Range( prj ) ) then
+ return fail;
+ fi;
+ return PreImagesRepresentativeNC( prj, g );
+end );
+
#############################################################################
##
#M KernelOfMultiplicativeGeneralMapping( ) . . . . . . . of projection
@@ -388,7 +412,7 @@ InstallMethod( SubdirectProductOp,"permgroup", true,
# over the generators of the kernel of $phi_2$.
gens := [];
for gen in GeneratorsOfGroup( G1 ) do
- Add( gens, gen^emb1 * PreImagesRepresentative(phi2,gen^phi1)^emb2 );
+ Add( gens, gen^emb1 * PreImagesRepresentativeNC(phi2,gen^phi1)^emb2 );
od;
for gen in GeneratorsOfGroup(
KernelOfMultiplicativeGeneralMapping( phi2 ) ) do
@@ -466,9 +490,10 @@ end );
#############################################################################
##
+#M PreImagesRepresentativeNC( , ) . . . . . . . . . . of projection
#M PreImagesRepresentative( , ) . . . . . . . . . . . of projection
##
-InstallMethod( PreImagesRepresentative,"perm subdirect product projection",
+InstallMethod( PreImagesRepresentativeNC,"perm subdirect product projection",
FamRangeEqFamElm,
[ IsProjectionSubdirectProductPermGroup,
IsMultiplicativeElementWithInverse ], 0,
@@ -487,17 +512,28 @@ InstallMethod( PreImagesRepresentative,"perm subdirect product projection",
# compute the preimage
if 1 = prj!.component then
- elm := img ^ info.perms[1]
- * PreImagesRepresentative(phi2,img^phi1) ^ info.perms[2];
+ elm := img ^ info.perms[1]
+ * PreImagesRepresentativeNC(phi2,img^phi1) ^ info.perms[2];
else
- elm := img ^ info.perms[2]
- * PreImagesRepresentative(phi1,img^phi2) ^ info.perms[1];
+ elm := img ^ info.perms[2]
+ * PreImagesRepresentativeNC(phi1,img^phi2) ^ info.perms[1];
fi;
# return the preimage
return elm;
end );
+InstallMethod( PreImagesRepresentative,"perm subdirect product projection",
+ FamRangeEqFamElm,
+ [ IsProjectionSubdirectProductPermGroup,
+ IsMultiplicativeElementWithInverse ], 0,
+ function( prj, img )
+ if not ( img in Range( prj ) ) then
+ return fail;
+ fi;
+ return PreImagesRepresentativeNC( prj, img );
+end );
+
#############################################################################
##
#M KernelOfMultiplicativeGeneralMapping( ) . . . . . . . of projection
@@ -799,9 +835,10 @@ end );
#############################################################################
##
+#M PreImagesRepresentativeNC( , ) . . . . . . . . . . of embedding
#M PreImagesRepresentative( , ) . . . . . . . . . . . of embedding
##
-InstallMethod( PreImagesRepresentative,
+InstallMethod( PreImagesRepresentativeNC,
"imprim perm wreath product embedding", FamRangeEqFamElm,
[ IsEmbeddingImprimitiveWreathProductPermGroup,
IsMultiplicativeElementWithInverse ], 0,
@@ -820,6 +857,16 @@ InstallMethod( PreImagesRepresentative,
^ (info.perms[ emb!.component ] ^ -1);
end );
+InstallMethod( PreImagesRepresentative,
+ "imprim perm wreath product embedding", FamRangeEqFamElm,
+ [ IsEmbeddingImprimitiveWreathProductPermGroup,
+ IsMultiplicativeElementWithInverse ], 0,
+ function( emb, g )
+ if not ( g in Range( emb ) ) then
+ return fail;
+ fi;
+ return PreImagesRepresentativeNC( emb, g );
+end );
#############################################################################
##
diff --git a/lib/grp.gd b/lib/grp.gd
index f9127d72c0..2a83f80eba 100644
--- a/lib/grp.gd
+++ b/lib/grp.gd
@@ -4250,8 +4250,8 @@ DeclareGlobalFunction( "AllSmallNonabelianSimpleGroups" );
## returns an isomorphism from G onto an isomorphic pc group.
## The series chosen for this pc representation depends on
## the method chosen.
-## G must be a polycyclic group of any kind, for example a solvable
-## permutation group.
+## G must be a finite polycyclic group of any kind, for example a solvable
+## permutation group. If G is finite but not solvable, fail is returned.
## G := Group( (1,2,3), (3,4,1) );;
## gap> iso := IsomorphismPcGroup( G );
@@ -4278,8 +4278,8 @@ DeclareAttribute( "IsomorphismPcGroup", IsGroup );
## returns an isomorphism from G onto an isomorphic pc group
## whose family pcgs is a special pcgs.
## (This can be beneficial to the runtime of calculations.)
-## G may be a polycyclic group of any kind, for example a solvable
-## permutation group.
+## G must be a finite polycyclic group of any kind, for example a solvable
+## permutation group. If G is finite but not solvable, fail is returned.
##
##
## <#/GAPDoc>
diff --git a/lib/grp.gi b/lib/grp.gi
index e46a66da6f..27f3644271 100644
--- a/lib/grp.gi
+++ b/lib/grp.gi
@@ -515,12 +515,12 @@ local p, hom, reps, as, a, b, ap, bp, ab, ap_bp, ab_p, g, h, H, N;
reps := ConjugacyClasses(Image(hom));
reps := List(reps, Representative);
reps := Filtered(reps, g -> not IsOne(g));
- reps := List(reps, g -> PreImagesRepresentative(hom, g));
+ reps := List(reps, g -> PreImagesRepresentativeNC(hom, g));
as := List(reps, a -> [a,a^p]);
for b in Image(hom) do
- b := PreImagesRepresentative(hom, b);
+ b := PreImagesRepresentativeNC(hom, b);
bp := b^p;
for a in as do
ap := a[2]; a := a[1];
@@ -1793,7 +1793,7 @@ local hom,gens;
fi;
hom:=IsomorphismPermGroup(G);
gens:=IndependentGeneratorsOfAbelianGroup(Image(hom,G));
- return List(gens,i->PreImagesRepresentative(hom,i));
+ return List(gens,i->PreImagesRepresentativeNC(hom,i));
end);
@@ -2090,8 +2090,8 @@ InstallGlobalFunction( SupersolvableResiduumDefault, function( G )
# dual space of the module, w.r.t. `pcgs'.
mg:= List( gs, x -> TransposedMat( List( pcgs,
y -> one * ExponentsOfPcElement( pcgs, Image( ph,
- Image( dh, PreImagesRepresentative(
- dh, PreImagesRepresentative(ph,y) )^x ) ) )))^-1);
+ Image( dh, PreImagesRepresentativeNC(
+ dh, PreImagesRepresentativeNC(ph,y) )^x ) ) )))^-1);
#T inverting is not necessary, or?
mg:= Filtered( mg, x -> x <> idm );
@@ -2141,11 +2141,11 @@ InstallGlobalFunction( SupersolvableResiduumDefault, function( G )
# Construct a group element corresponding to
# the basis element of the submodule.
- Add( tmp2, PreImagesRepresentative( ph,
+ Add( tmp2, PreImagesRepresentativeNC( ph,
PcElementByExponentsNC( pcgs, v ) ) );
od;
- Add( ds, PreImagesSet( dh,
+ Add( ds, PreImagesSetNC( dh,
SubgroupNC( df, Concatenation( tmp2, gen ) ) ) );
od;
Append( gen, tmp2 );
@@ -2154,14 +2154,14 @@ InstallGlobalFunction( SupersolvableResiduumDefault, function( G )
else
# cyclic case
- Add( ds, PreImagesSet( dh,
+ Add( ds, PreImagesSetNC( dh,
SubgroupNC( df, AsSSortedList( gen ) ) ) );
fi;
od;
# Generate the new candidate.
- ssr:= PreImagesSet( dh, SubgroupNC( df, AsSSortedList( gen ) ) );
+ ssr:= PreImagesSetNC( dh, SubgroupNC( df, AsSSortedList( gen ) ) );
fi;
@@ -2392,7 +2392,7 @@ InstallMethod( UpperCentralSeriesOfGroup,
Add( S, C );
Info( InfoGroup, 2, "UpperCentralSeriesOfGroup: step ", Length(S) );
hom := NaturalHomomorphismByNormalSubgroupNC( G, C );
- C := PreImages( hom, Centre( Image( hom ) ) );
+ C := PreImagesNC( hom, Centre( Image( hom ) ) );
od;
if Last(S) = G then
@@ -3598,7 +3598,7 @@ InstallMethod( HallSubgroupOp,
iso := IsomorphismPermGroup( G );
H := HallSubgroup( ImagesSource( iso ), pi );
- return PreImagesSet(iso, H);
+ return PreImagesSetNC(iso, H);
end );
@@ -5337,7 +5337,7 @@ InstallMethod (MinimalNormalSubgroups,
local hom;
hom := NiceMonomorphism (grp);
return List (MinimalNormalSubgroups (NiceObject (grp)),
- N -> PreImagesSet (hom, N));
+ N -> PreImagesSetNC(hom, N));
end);
diff --git a/lib/grpcompl.gi b/lib/grpcompl.gi
index 9adf68a175..5058cd8610 100644
--- a/lib/grpcompl.gi
+++ b/lib/grpcompl.gi
@@ -100,11 +100,11 @@ local G,N,K,s, h, q, fpi, factorpres, com, comgens, cen, ocrels, fpcgs, ncom,
factorpres:=[FreeGeneratorsOfFpGroup(Range(fpi)),
RelatorsOfFpGroup(Range(fpi)),
List(GeneratorsOfGroup(Range(fpi)),
- i->PreImagesRepresentative(fpi,i))];
- Assert(1,ForAll(factorpres[3],i->Image(h,PreImagesRepresentative(h,i))=i));
+ i->PreImagesRepresentativeNC(fpi,i))];
+ Assert(1,ForAll(factorpres[3],i->Image(h,PreImagesRepresentativeNC(h,i))=i));
# initialize
com:=[G];
- comgens:=[List(factorpres[3],i->PreImagesRepresentative(h,i))];
+ comgens:=[List(factorpres[3],i->PreImagesRepresentativeNC(h,i))];
cen:=[s[1]];
ocrels:=false;
diff --git a/lib/grpfp.gd b/lib/grpfp.gd
index eaa41d6421..8e373a6ec3 100644
--- a/lib/grpfp.gd
+++ b/lib/grpfp.gd
@@ -90,9 +90,9 @@ fi;
## [5] CosetTableInWholeGroup( H )
## @ GAPROOT/lib/grpfp.gi:1733
## ... at *stdin*:3
-## type 'return;' if you want to continue with a new limit of 8192000 cosets,
-## type 'quit;' if you want to quit the coset enumeration,
-## type 'maxlimit := 0; return;' in order to continue without a limit
+## you can enter 'return;' to continue with a new limit of 8192000 cosets,
+## you can enter 'quit;' to abort the coset enumeration,
+## you can enter 'maxlimit := 0; return;' in order to continue without a limit
## brk> quit;
## ]]>
##
diff --git a/lib/grpfp.gi b/lib/grpfp.gi
index 8f9d97983b..414ee482c8 100644
--- a/lib/grpfp.gi
+++ b/lib/grpfp.gi
@@ -319,7 +319,7 @@ local fam,hom;
if hom=fail then
TryNextMethod();
fi;
- return PreImagesRepresentative(hom,Random(rs, Image(hom,gp)));
+ return PreImagesRepresentativeNC(hom,Random(rs, Image(hom,gp)));
end );
#############################################################################
@@ -1113,10 +1113,10 @@ BindGlobal("GTC_CosetTableFromGensAndRels",function(arg)
# to give tidy instructions if one enters a break-loop
SavedOnBreakMessage := OnBreakMessage;
TCEOnBreakMessage := function(n)
- Print( "type 'return;' if you want to continue with a new limit of ",
+ Print( "you can enter 'return;' to continue with a new limit of ",
n, " cosets,\n",
- "type 'quit;' if you want to quit the coset enumeration,\n",
- "type 'maxlimit := 0; return;' in order to continue without a ",
+ "you can enter 'quit;' to abort the coset enumeration,\n",
+ "you can enter 'maxlimit := 0; return;' in order to continue without a ",
"limit\n" );
OnBreakMessage := SavedOnBreakMessage;
end;
@@ -2031,11 +2031,11 @@ local d,A,B,e1,e2,Ag,Bg,s,sg,u,v,map,sz;
# instead of intersecting both preimages with s we only intersect the
# intersection
- u:=PreImagesSet(Projection(d,1),G!.sub);
+ u:=PreImagesSetNC(Projection(d,1),G!.sub);
if HasSize(B) then
SetSize(u,Size(G!.sub)*Size(B));
fi;
- v:=PreImagesSet(Projection(d,2),H!.sub);
+ v:=PreImagesSetNC(Projection(d,2),H!.sub);
if HasSize(A) then
SetSize(v,Size(H!.sub)*Size(A));
fi;
@@ -3167,7 +3167,7 @@ InstallMethod( LowIndexSubgroupsFpGroupIterator,
local u, v;
u:= NextIterator( iter!.fullIterator );
- v:= PreImagesSet( fpi, u );
+ v:= PreImagesSetNC( fpi, u );
SetIndexInWholeGroup( v,
IndexInWholeGroup( G ) * IndexInWholeGroup( u ) );
return v;
@@ -3236,7 +3236,7 @@ local fpi,u,l,i,a;
l:=[];
for i in u do
- a:=PreImagesSet(fpi,i);
+ a:=PreImagesSetNC(fpi,i);
SetIndexInWholeGroup(a,IndexInWholeGroup(G)*IndexInWholeGroup(i));
Add(l,a);
od;
@@ -3379,8 +3379,8 @@ local d,A,B,e1,e2,Ag,Bg,s,sg,u,v;
# get both subgroups in the direct product via the projections
# instead of intersecting both preimages with s we only intersect the
# intersection
- u:=PreImagesSet(Projection(d,1),G!.sub);
- v:=PreImagesSet(Projection(d,2),H!.sub);
+ u:=PreImagesSetNC(Projection(d,1),G!.sub);
+ v:=PreImagesSetNC(Projection(d,2),H!.sub);
u:=Intersection(u,s);
v:=Intersection(v,s);
@@ -4332,7 +4332,7 @@ local s, a, hom;
fi;
hom:=EpimorphismSolvableQuotient(G,s);
if Size(Image(hom))<>s then
- Error("group is not solvable");
+ return fail;
else
SetIsInjective(hom, true);
fi;
@@ -5497,7 +5497,7 @@ local G,T,gens,g,reps,ng,index,i,j,ndef,n,iso;
subgroup := U,
iso:=iso,
table:=T,
- reps:=List(reps,i->PreImagesRepresentative(iso,i))));
+ reps:=List(reps,i->PreImagesRepresentativeNC(iso,i))));
fi;
ndef := 1;
@@ -5517,7 +5517,7 @@ local G,T,gens,g,reps,ng,index,i,j,ndef,n,iso;
subgroup := U,
iso:=iso,
table:=T,
- reps:=List(reps,i->PreImagesRepresentative(iso,i))));
+ reps:=List(reps,i->PreImagesRepresentativeNC(iso,i))));
fi;
fi;
od;
diff --git a/lib/grplatt.gi b/lib/grplatt.gi
index 5563219bf7..7419486e85 100644
--- a/lib/grplatt.gi
+++ b/lib/grplatt.gi
@@ -955,7 +955,7 @@ InstallGlobalFunction(LatticeViaRadical,function(arg)
#k:=PreImage(hom,a);
# make generators of homomorphism fit nicely to presentation
gf:=IsomorphismFpGroup(a);
- e:=List(MappingGeneratorsImages(gf)[1],x->PreImagesRepresentative(hom,x));
+ e:=List(MappingGeneratorsImages(gf)[1],x->PreImagesRepresentativeNC(hom,x));
# we cannot guarantee that the parent contains e, so no
# ClosureSubgroup.
k:=ClosureGroup(KernelOfMultiplicativeGeneralMapping(hom),e);
@@ -2779,7 +2779,7 @@ local fgi,inducedfactorautos,projs,psubs,info,n,l,nl,emb,u,pos,
auts:=[];
for i in GeneratorsOfGroup(n) do
aut:=GroupHomomorphismByImages(f,f,gens,List(gens,x->
- Image(hom,PreImagesRepresentative(hom,x)^i)));
+ Image(hom,PreImagesRepresentativeNC(hom,x)^i)));
SetIsBijective(aut,true);
Add(auts,aut);
od;
@@ -2856,7 +2856,7 @@ local fgi,inducedfactorautos,projs,psubs,info,n,l,nl,emb,u,pos,
for dc in DoubleCosetRepsAndSizes(t[7],ind,t[8]) do
# form the subdirect product
g:=List(GeneratorsOfGroup(j[1]),
- x->x*Image(emb,PreImagesRepresentative(t[5],
+ x->x*Image(emb,PreImagesRepresentativeNC(t[5],
Image(dc[1],Image(iso,x))) ));
Append(g,List(GeneratorsOfGroup(t[1]),x->Image(emb,x)));
g:=Subgroup(D,g);
diff --git a/lib/grpmat.gi b/lib/grpmat.gi
index 5766951a76..25d07eab9b 100644
--- a/lib/grpmat.gi
+++ b/lib/grpmat.gi
@@ -424,13 +424,11 @@ local field, dict, acts, start, j, zerov, zero, dim, base, partbas, heads,
SetRange(hom,R);
SetImagesSource(hom,R);
SetMappingGeneratorsImages(hom,[acts,permimg]);
-# p:=RUN_IN_GGMBI; # no niceomorphism translation here
-# RUN_IN_GGMBI:=true;
+# # no niceomorphism translation here
# SetAsGroupGeneralMappingByImages ( hom, GroupHomomorphismByImagesNC
-# ( G, R, acts, permimg ) );
+# ( G, R, acts, permimg : Run_In_GGMBI:= true ) );
#
# SetFilterObj( hom, IsActionHomomorphismByBase );
-# RUN_IN_GGMBI:=p;
if act=OnRight or act=OnPoints then
# only store for action on right. projective action needs is own call to
# `LinearActionBase' as this will set other needed parameters.
@@ -623,7 +621,7 @@ local gens,s,dom,mon,no;
# call the recursive function to do the work
gens:= SCMinSmaGens( no, s, [], One( no ), true ).gens;
SetMinimalStabChain(G,s);
- return List(gens,i->PreImagesRepresentative(mon,i));
+ return List(gens,i->PreImagesRepresentativeNC(mon,i));
end);
#############################################################################
@@ -660,7 +658,7 @@ local s,dom,mon, img;
i->Position(HomeEnumerator(dom),i))));
# call the recursive function to do the work
s:= LargestElementStabChain( s, One( img ) );
- return PreImagesRepresentative(mon,s);
+ return PreImagesRepresentativeNC(mon,s);
end);
#############################################################################
@@ -699,7 +697,7 @@ local mon,dom,S,o,oimgs,p,i,g;
od;
# change by corresponding matrix element
- e:=PreImagesRepresentative(mon,g)*e;
+ e:=PreImagesRepresentativeNC(mon,g)*e;
S:=S.stabilizer;
od;
@@ -1202,9 +1200,10 @@ InstallMethod( ImagesRepresentative,
#############################################################################
##
-#M PreImagesRepresentative( , ) . . . for a blow up isomorphism
+#M PreImagesRepresentativeNC( , ) . . . for a blow up isomorphism
+#M PreImagesRepresentative( , ) . . . . for a blow up isomorphism
##
-InstallMethod( PreImagesRepresentative,
+InstallMethod( PreImagesRepresentativeNC,
"for a blow up isomorphism, and a matrix in the range",
FamRangeEqFamElm,
[ IsBlowUpIsomorphism, IsMatrix ],
@@ -1257,6 +1256,17 @@ InstallMethod( PreImagesRepresentative,
return preim;
end );
+InstallMethod( PreImagesRepresentative,
+ "for a blow up isomorphism, and a matrix in the range",
+ FamRangeEqFamElm,
+ [ IsBlowUpIsomorphism, IsMatrix ],
+ function( iso, mat )
+ if not ( mat in Range(iso) ) then
+ return fail;
+ fi;
+ return PreImagesRepresentativeNC( iso, mat );
+ end );
+
#############################################################################
##
@@ -1341,7 +1351,12 @@ InstallMethod( ConjugateGroup, ", ", IsCollsElms,
if HasIsSubgroupSL( G ) then
SetIsSubgroupSL( H, IsSubgroupSL( G ) );
fi;
- F:= FieldOfMatrixList( [ g ] );
+
+ F:= DefaultScalarDomainOfMatrixList( [ g ] );
+ if not IsField( F ) then
+ return H;
+ fi;
+
if HasInvariantBilinearForm( G ) then
if not IsBound( ginv ) then
ginv := g^-1;
diff --git a/lib/grpnames.gi b/lib/grpnames.gi
index 8220d79e88..695923570d 100644
--- a/lib/grpnames.gi
+++ b/lib/grpnames.gi
@@ -173,7 +173,7 @@ InstallMethod( NormalComplementNC,
i:=0;
for gF in IndependentGeneratorsOfAbelianGroup(F) do
i := i+1;
- g := PreImagesRepresentative(nat, gF);
+ g := PreImagesRepresentativeNC(nat, gF);
R := RightCoset(N, g);
# DirectFactorsOfGroup already computed Center and RationalClasses
# when calling NormalComplement
@@ -893,9 +893,11 @@ InstallMethod( DecompositionTypesOfGroup,
# abelian special case
if IsAbelian(G) then
AG := AbelianInvariants(G);
- if Length(AG) = 1 then DTypes := Set([AG[1]]); else
+ if Length(AG) = 1 then
+ DTypes := Set([AG[1]]);
+ else
T := ["x"];
- for a in AG do Add(T,a); od;
+ Append(T, AG);
DTypes := Set([T]);
fi;
return DTypes;
@@ -942,7 +944,9 @@ InstallMethod( DecompositionTypesOfGroup,
od;
# default: a non-split extension
- if Length(DTypes) = 0 then DTypes := Set([["non-split",Size(G)]]); fi;
+ if Length(DTypes) = 0 then
+ DTypes := Set([["non-split",Size(G)]]);
+ fi;
return DTypes;
end );
@@ -999,9 +1003,8 @@ function(G)
gens := DoComputeDihedralGenerators(G);
if gens = fail then
return false;
- else
- SetDihedralGenerators(G, gens);
fi;
+ SetDihedralGenerators(G, gens);
return true;
end);
@@ -1198,27 +1201,31 @@ InstallMethod( IsAlternatingGroup,
function ( G )
- local n, ids, info;
+ local info;
if not IsFinite(G) then TryNextMethod(); fi;
- if IsNaturalAlternatingGroup(G) then return true;fi;
- if Size(G) < 60 then
+ if IsNaturalAlternatingGroup(G) then
+ return true;
+ elif Size(G) < 60 then
if Size(G) = 1 then
- SetAlternatingDegree(G,0); return true;
+ SetAlternatingDegree(G,0);
+ return true;
elif Size(G) = 3 then
- SetAlternatingDegree(G,3); return true;
+ SetAlternatingDegree(G,3);
+ return true;
elif Size(G) = 12 and Size(DerivedSubgroup(G)) = 4 then
- SetAlternatingDegree(G,4); return true;
- else return false; fi;
+ SetAlternatingDegree(G,4);
+ return true;
+ fi;
+ elif IsSimpleGroup(G) then
+ info := IsomorphismTypeInfoFiniteSimpleGroup(G);
+ if info.series = "A" then
+ SetAlternatingDegree(G,info.parameter);
+ return true;
+ fi;
fi;
-
- if not IsSimpleGroup(G) then return false; fi;
-
- info := IsomorphismTypeInfoFiniteSimpleGroup(G);
- if info.series = "A"
- then SetAlternatingDegree(G,info.parameter); return true;
- else return false; fi;
+ return false;
end );
#############################################################################
@@ -1272,7 +1279,9 @@ InstallMethod( IsSymmetricGroup,
if not IsFinite(G) then TryNextMethod(); fi;
# special treatment of small cases
- if Size(G)<=2 then SetSymmetricDegree(G,Size(G)); return true;
+ if Size(G)<=2 then
+ SetSymmetricDegree(G,Size(G));
+ return true;
elif Size(G)=6 and not IsAbelian(G) then
SetSymmetricDegree(G,3);
return true;
@@ -1407,15 +1416,15 @@ InstallGlobalFunction( LinearGroupParameters,
if not IsPosInt(N) then Error(" must be positive integer"); fi;
- # Formeln:
+ # Formulas:
# |GL(n, q)| = Product(q^n - q^k : k in [0..n-1])
# |SL(n, q)| = |GL(n, q)| / (q - 1)
# |PSL(n, q)| = |SL(n, q)| / gcd(n, q - 1)
- # mit q = p^e f"ur p prim, e >= 1, n >= 1.
+ # where q = p^e for p prime, e >= 1, n >= 1.
- # Betrachte N = |GL(n,q)|. Dann gilt f"ur n >= 2
- # (1) nu_p(N) = e * Binomial(n,2) und
- # (2) (q - 1)^n teilt N.
+ # Consider N = |GL(n,q)|. Then we have for n >= 2
+ # (1) nu_p(N) = e * Binomial(n,2) and
+ # (2) (q - 1)^n divides N.
npeGL := [ ]; npeSL := [ ]; npePSL := [ ];
if N = 1 then
return rec( npeGL := npeGL, npeSL := npeSL, npePSL := npePSL );
@@ -1470,8 +1479,9 @@ InstallMethod( IsPSL,
# more than one npe-triple should only
# occur in the cases |G| in [60, 168, 20160]
- if Length(npes) > 1 and not( Size(G) in [60, 168, 20160] )
- then Error("algebraic panic! probably npe does not work"); fi;
+ if Length(npes) > 1 and not( Size(G) in [60, 168, 20160] ) then
+ Error("algebraic panic! probably npe does not work");
+ fi;
# set the parameters
npe := npes[1];
@@ -1483,12 +1493,10 @@ InstallMethod( IsPSL,
# PSL(2, 2)
if npes[1] = [2, 2, 1] then
if IsAbelian(G) then return false; fi;
- SetParametersOfGroupViewedAsPSL(G,npe); return true;
# PSL(2, 3)
elif npes[1] = [2, 3, 1] then
if Size(DerivedSubgroup(G)) <> 4 then return false; fi;
- SetParametersOfGroupViewedAsPSL(G,npe); return true;
# PSL(3, 4) / PSL(4, 2) \cong A_8
elif npes = [ [ 4, 2, 1 ], [ 3, 2, 2 ] ] then
@@ -1497,13 +1505,13 @@ InstallMethod( IsPSL,
else
npe := npes[2];
fi;
- SetParametersOfGroupViewedAsPSL(G,npe); return true;
# other cases
- else
- if not IsSimpleGroup(G) then return false; fi;
- SetParametersOfGroupViewedAsPSL(G,npe); return true;
+ elif not IsSimpleGroup(G) then
+ return false;
fi;
+ SetParametersOfGroupViewedAsPSL(G,npe);
+ return true;
end );
#############################################################################
@@ -1563,12 +1571,10 @@ InstallMethod( IsSL,
# SL(2, 2)
if npes = [2, 2, 1] then
if IsAbelian(G) then return false; fi;
- SetParametersOfGroupViewedAsSL(G,npes); return true;
# SL(2, 3)
elif npes = [2, 3, 1] then
if Size(DerivedSubgroup(G)) <> 8 then return false; fi;
- SetParametersOfGroupViewedAsSL(G,npes); return true;
# other cases, in which the contained PSL is simple
else
@@ -1583,8 +1589,9 @@ InstallMethod( IsSL,
then return false; fi;
if IsomorphismGroups(G,SL(npes[1],npes[2]^npes[3])) = fail
then return false; fi;
- SetParametersOfGroupViewedAsSL(G,npes); return true;
fi;
+ SetParametersOfGroupViewedAsSL(G,npes);
+ return true;
end );
#############################################################################
@@ -1649,7 +1656,6 @@ InstallMethod( IsGL,
# GL(2, 2)
if npes = [2, 2, 1] then
if IsAbelian(G) then return false; fi;
- SetParametersOfGroupViewedAsGL(G,npes); return true;
# GL(2, 3)
elif npes = [2, 3, 1] then
@@ -1668,7 +1674,6 @@ InstallMethod( IsGL,
# elements of order 4 in one case, and 2 in the other; this is also
# how e.g. IdGroup distinguishes them
if Number(G, g -> Order(g) = 2) < 13 then return false; fi;
- SetParametersOfGroupViewedAsGL(G,npes); return true;
# other cases, in which contained PSL is simple
else
@@ -1687,8 +1692,9 @@ InstallMethod( IsGL,
then return false; fi;
if IsomorphismGroups(G,GL(npes[1],npes[2]^npes[3])) = fail
then return false; fi;
- SetParametersOfGroupViewedAsGL(G,npes); return true;
fi;
+ SetParametersOfGroupViewedAsGL(G,npes);
+ return true;
end );
#############################################################################
@@ -1728,23 +1734,21 @@ InstallMethod( GLUnderlyingField,
BindGlobal( "SD_insertsep", # function to join parts of name
function ( strs, sep, brack )
- local short, s, i;
-
- short := ValueOption("short") = true;
+ local s, i;
if strs = [] then return ""; fi;
strs := Filtered(strs,str->str<>"");
if Length(strs) > 1 then
for i in [1..Length(strs)] do
- if Intersection(strs[i],brack) <> ""
- then strs[i] := Concatenation("(",strs[i],")"); fi;
+ if Intersection(strs[i],brack) <> "" then
+ strs[i] := Concatenation("(",strs[i],")");
+ fi;
od;
fi;
- s := strs[1];
- for i in [2..Length(strs)] do
- s := Concatenation(s,sep,strs[i]);
- od;
- if short then RemoveCharacters(s," "); fi;
+ s := JoinStringsWithSeparator(strs,sep);
+ if ValueOption("short") = true then
+ RemoveCharacters(s," ");
+ fi;
return s;
end);
@@ -1759,27 +1763,29 @@ BindGlobal( "SD_cyclic",
BindGlobal( "SD_cycsaspowers", # function to write C2 x C2 x C2 as 2^3, etc.
function ( name, cycsizes )
- local short, g, d, k, j, n;
+ local g, d, k, j, n;
- short := ValueOption("short") = true;
- if not short then return name; fi;
+ if ValueOption("short") <> true then
+ return name;
+ fi;
RemoveCharacters(name," ");
- cycsizes := Collected(cycsizes);
- for n in cycsizes do
- d := n[1]; k := n[2];
- g := SD_cyclic(d);
- if d = 0 then
- d := "Z";
- else
- d := String(d);
- fi;
- if k > 1 then
- for j in Reversed([2..k]) do
- name := ReplacedString(name,SD_insertsep(List([1..j],i->g),"x",""),
- Concatenation(d,"^",String(j)));
- od;
- fi;
- od;
+ cycsizes := Collected(cycsizes);
+ for n in cycsizes do
+ d := n[1];
+ k := n[2];
+ g := SD_cyclic(d);
+ if d = 0 then
+ d := "Z";
+ else
+ d := String(d);
+ fi;
+ if k > 1 then
+ for j in Reversed([2..k]) do
+ name := ReplacedString(name,SD_insertsep(List([1..j],i->g),"x",""),
+ Concatenation(d,"^",String(j)));
+ od;
+ fi;
+ od;
RemoveCharacters(name,"C");
return name;
end);
@@ -1810,11 +1816,14 @@ BindGlobal( "StructureDescriptionForFiniteSimpleGroups", # for simple groups
parameter; # parameters of G in series
# special case abelian group
- if IsAbelian(G) then return StructureDescriptionForAbelianGroups(G); fi;
+ if IsAbelian(G) then
+ return StructureDescriptionForAbelianGroups(G);
+ fi;
# special case alternating group
- if IsAlternatingGroup(G)
- then return Concatenation("A",String(AlternatingDegree(G))); fi;
+ if IsAlternatingGroup(G) then
+ return Concatenation("A",String(AlternatingDegree(G)));
+ fi;
# special case PSL
if IsPSL(G) then
@@ -1913,30 +1922,39 @@ BindGlobal( "StructureDescriptionForFiniteGroups", # for finite groups
fi;
# special case trivial group
- if IsTrivial(G) then return "1"; fi;
+ if IsTrivial(G) then
+ return "1";
+ fi;
# special case abelian group
- if IsAbelian(G) then return StructureDescriptionForAbelianGroups(G); fi;
+ if IsAbelian(G) then
+ return StructureDescriptionForAbelianGroups(G);
+ fi;
# special case alternating group
- if IsAlternatingGroup(G)
- then return Concatenation("A",String(AlternatingDegree(G))); fi;
+ if IsAlternatingGroup(G) then
+ return Concatenation("A",String(AlternatingDegree(G)));
+ fi;
# special case symmetric group
- if IsSymmetricGroup(G)
- then return Concatenation("S",String(SymmetricDegree(G))); fi;
+ if IsSymmetricGroup(G) then
+ return Concatenation("S",String(SymmetricDegree(G)));
+ fi;
# special case dihedral group
- if IsDihedralGroup(G) and Size(G) > 6
- then return Concatenation("D",String(Size(G))); fi;
+ if IsDihedralGroup(G) and Size(G) > 6 then
+ return Concatenation("D",String(Size(G)));
+ fi;
# special case quaternion group
- if IsQuaternionGroup(G)
- then return Concatenation("Q",String(Size(G))); fi;
+ if IsQuaternionGroup(G) then
+ return Concatenation("Q",String(Size(G)));
+ fi;
# special case quasidihedral group
- if IsQuasiDihedralGroup(G)
- then return Concatenation("QD",String(Size(G))); fi;
+ if IsQuasiDihedralGroup(G) then
+ return Concatenation("QD",String(Size(G)));
+ fi;
# special case PSL
if IsPSL(G) then
@@ -1975,7 +1993,9 @@ BindGlobal( "StructureDescriptionForFiniteGroups", # for finite groups
cycsizes := Filtered(cycsizes,n->n<>1);
cycname := SD_cycsaspowers(SD_insertsep(List(cycsizes, SD_cyclic),
" x ",":."), cycsizes);
- else cycname := ""; fi;
+ else
+ cycname := "";
+ fi;
noncyclics := Difference(Gs,cyclics);
noncycname := SD_insertsep(List(noncyclics,StructureDescription),
" x ",":.");
@@ -2049,32 +2069,33 @@ BindGlobal( "StructureDescriptionForFiniteGroups", # for finite groups
# non-splitting, non-simple group
if not IsTrivial(Centre(G)) then
cname := SD_insertsep([StructureDescription(Centre(G)),
- StructureDescription(G/Centre(G))]," . ","x:.");
+ StructureDescription(G/Centre(G))],
+ " . ","x:.");
fi;
if not IsPerfectGroup(G) then
dname := SD_insertsep([StructureDescription(DerivedSubgroup(G)),
StructureDescription(G/DerivedSubgroup(G))],
" . ","x:.");
fi;
- if IsBound(cname) and IsBound(dname) and cname <> dname
- then return Concatenation(cname," = ",dname);
- elif IsBound(cname) then return cname;
- elif IsBound(dname) then return dname;
- elif not IsTrivial(FrattiniSubgroup(G))
- then return SD_insertsep([StructureDescription(FrattiniSubgroup(G)),
- StructureDescription(G/FrattiniSubgroup(G))],
- " . ","x:.");
- elif IsPosInt(NrPerfectGroups(Size(G)))
- and not Size(G) in [ 86016, 368640, 737280 ]
- # this does not happen for Size(G)<10^6
- then
- id := PerfectIdentification(G);
- return Concatenation("PerfectGroup(",String(id[1]),",",
- String(id[2]),")");
- else return Concatenation("");
+ if IsBound(cname) and IsBound(dname) and cname <> dname then
+ return Concatenation(cname," = ",dname);
+ elif IsBound(cname) then
+ return cname;
+ elif IsBound(dname) then
+ return dname;
+ elif not IsTrivial(FrattiniSubgroup(G)) then
+ return SD_insertsep([StructureDescription(FrattiniSubgroup(G)),
+ StructureDescription(G/FrattiniSubgroup(G))],
+ " . ","x:.");
+ elif IsPosInt(NrPerfectGroups(Size(G))) then
+ id := PerfectIdentification(G);
+ return Concatenation("PerfectGroup(",String(id[1]),",",
+ String(id[2]),")");
+ else
+ return Concatenation("");
fi;
end );
diff --git a/lib/grpnice.gd b/lib/grpnice.gd
index 5a9480fd86..8d7dee5536 100644
--- a/lib/grpnice.gd
+++ b/lib/grpnice.gd
@@ -189,6 +189,9 @@ InstallSubsetMaintenance( IsHandledByNiceMonomorphism,
IsHandledByNiceMonomorphism and IsGroup,
IsGroup);
+# We recommend the (documented) global option `Run_In_GGMBI`
+# instead of the global variable `RUN_IN_GGMBI`,
+# but `RUN_IN_GGMBI` is still supported because GAP packages might use it.
RUN_IN_GGMBI:=false; # If somebody would call `GHBI' to make a
# NiceMonomorphism, we would get an infinite recursion.
# This flag can be set to avoid GHBIs to be translated
@@ -363,7 +366,7 @@ BindGlobal( "AttributeMethodByNiceMonomorphismList", function( oper, par )
local nice;
nice:= NiceMonomorphism( obj );
return List( oper( NiceObject( obj ) ),
- x -> PreImagesRepresentative( nice, x ) );
+ x -> PreImagesRepresentativeNC( nice, x ) );
end );
end );
@@ -398,7 +401,7 @@ BindGlobal( "AttributeMethodByNiceMonomorphismCollElm", function( oper, par )
img := ImagesRepresentative( nice, obj2 : actioncanfail:= true );
if img = fail or
not ( img in ImagesSource( nice ) and
- PreImagesRepresentative( nice, img ) = obj2 ) then
+ PreImagesRepresentativeNC( nice, img ) = obj2 ) then
TryNextMethod();
fi;
return oper( NiceObject( obj1 ), img );
@@ -441,7 +444,7 @@ BindGlobal( "AttributeMethodByNiceMonomorphismElmColl",
img := ImagesRepresentative( nice, obj1 : actioncanfail:= true );
if img = fail or
not (img in ImagesSource( nice ) and
- PreImagesRepresentative( nice, img ) = obj1) then
+ PreImagesRepresentativeNC( nice, img ) = obj1) then
TryNextMethod();
fi;
return oper( img, NiceObject( obj2 ) );
@@ -525,7 +528,7 @@ BindGlobal( "GroupMethodByNiceMonomorphismCollElm",
img := ImagesRepresentative( nice, obj2 : actioncanfail:= true );
if img = fail or
not (img in ImagesSource( nice ) and
- PreImagesRepresentative( nice, img ) = obj2) then
+ PreImagesRepresentativeNC( nice, img ) = obj2) then
TryNextMethod();
fi;
img1 := oper( NiceObject( obj1 ), img );
@@ -613,7 +616,7 @@ BindGlobal( "SubgroupMethodByNiceMonomorphismCollColl", function( oper, par )
img:=ImagesSet( nice, obj2 );
if img = fail or
not ( IsSubset( ImagesSource( nice ), img ) and
- PreImagesSet( nice, img ) = obj2 ) then
+ PreImagesSetNC( nice, img ) = obj2 ) then
TryNextMethod();
fi;
img := oper( NiceObject( obj1 ), img );
@@ -637,7 +640,7 @@ BindGlobal( "SubgroupMethodByNiceMonomorphismCollElm", function( oper, par )
img := ImagesRepresentative( nice, obj2 : actioncanfail:= true );
if img = fail or
not ( img in ImagesSource( nice ) and
- PreImagesRepresentative (nice , img ) = obj2 ) then
+ PreImagesRepresentativeNC( nice, img ) = obj2 ) then
TryNextMethod();
fi;
img1 := oper( NiceObject( obj1 ), img );
@@ -764,7 +767,7 @@ BindGlobal( "GroupSeriesMethodByNiceMonomorphismCollElm",
img := ImagesRepresentative( nice, obj2 : actioncanfail:= true );
if img = fail or
not ( img in ImagesSource( nice ) and
- PreImagesRepresentative( nice, img ) = obj2 ) then
+ PreImagesRepresentativeNC( nice, img ) = obj2 ) then
TryNextMethod();
fi;
list := ShallowCopy( oper( NiceObject( obj1 ), img ) );
diff --git a/lib/grpnice.gi b/lib/grpnice.gi
index f72d348e81..faf214a1f3 100644
--- a/lib/grpnice.gi
+++ b/lib/grpnice.gi
@@ -212,7 +212,7 @@ function( elm, G )
nice := NiceMonomorphism( G );
img := ImagesRepresentative( nice, elm:actioncanfail:=true );
return img<>fail and img in NiceObject( G )
- and PreImagesRepresentative( nice, img ) = elm;
+ and PreImagesRepresentativeNC( nice, img ) = elm;
end );
@@ -284,7 +284,7 @@ function( obj1, obj2 )
img := ImagesRepresentative( nice, obj2:actioncanfail:=true );
if img = fail or
not (img in ImagesSource(nice) and
- PreImagesRepresentative(nice,img)=obj2) then
+ PreImagesRepresentativeNC(nice,img)=obj2) then
TryNextMethod();
fi;
no:=NiceObject(obj1);
@@ -344,10 +344,10 @@ local mon,cl,clg,c,i;
cl:=ConjugacyClasses(NiceObject(g));
clg:=[];
for i in cl do
- c:=ConjugacyClass(g,PreImagesRepresentative(mon,Representative(i)));
+ c:=ConjugacyClass(g,PreImagesRepresentativeNC(mon,Representative(i)));
c!.niceClass:=i;
if HasStabilizerOfExternalSet(i) then
- SetStabilizerOfExternalSet(c,PreImages(mon,StabilizerOfExternalSet(i)));
+ SetStabilizerOfExternalSet(c,PreImagesNC(mon,StabilizerOfExternalSet(i)));
fi;
Add(clg,c);
od;
@@ -767,7 +767,7 @@ SubgroupMethodByNiceMonomorphism( SolvableRadical,
InstallMethodWithRandomSource( Random,
"for a random source and a group handled by nice monomorphism",
[ IsRandomSource, IsGroup and IsHandledByNiceMonomorphism ], 0,
- {rs, G} -> PreImagesRepresentative( NiceMonomorphism( G ),
+ {rs, G} -> PreImagesRepresentativeNC( NiceMonomorphism( G ),
Random( rs, NiceObject( G ) ) ) );
@@ -783,9 +783,9 @@ local mon,cl,clg,c,i;
cl:=RationalClasses(NiceObject(g));
clg:=[];
for i in cl do
- c:=RationalClass(g,PreImagesRepresentative(mon,Representative(i)));
+ c:=RationalClass(g,PreImagesRepresentativeNC(mon,Representative(i)));
if HasStabilizerOfExternalSet(i) then
- SetStabilizerOfExternalSet(c,PreImages(mon,StabilizerOfExternalSet(i)));
+ SetStabilizerOfExternalSet(c,PreImagesNC(mon,StabilizerOfExternalSet(i)));
fi;
if HasGaloisGroup(i) then
SetGaloisGroup(c,GaloisGroup(i));
@@ -806,7 +806,7 @@ function(g,u)
local mon,rt;
mon:=NiceMonomorphism(g);
rt:=RightTransversal(ImagesSet(mon,g),ImagesSet(mon,u));
- rt:=List(rt,i->RightCoset(u,PreImagesRepresentative(mon,i)));
+ rt:=List(rt,i->RightCoset(u,PreImagesRepresentativeNC(mon,i)));
return rt;
end);
@@ -878,7 +878,7 @@ local hom,rep;
rep:= RepresentativeAction( NiceObject( G ),
ImageElm( hom, a ), ImageElm( hom, b ), OnPoints );
if rep<>fail then
- rep:=PreImagesRepresentative(hom,rep);
+ rep:=PreImagesRepresentativeNC(hom,rep);
fi;
return rep;
end);
@@ -927,16 +927,22 @@ InstallMethod( GroupGeneralMappingByImagesNC,
"from a group handled by a niceomorphism",true,
[ IsGroup and IsHandledByNiceMonomorphism, IsGroup, IsList, IsList ], 0,
function( G, H, gens, imgs )
-local nice,geni,map2,tmp;
- if RUN_IN_GGMBI=true then
+local nice,geni,map2;
+ if ValueOption( "Run_In_GGMBI" ) = true then
+ TryNextMethod();
+ elif RUN_IN_GGMBI = true then
+ # Code was called that does not know about the global option.
+ # Make it work but print a warning.
+ Info( InfoWarning, 1,
+ "use the global option 'Run_In_GGMBI' not the global variable ",
+ "'RUN_IN_GGMBI', see '?Run_In_GGMBI'" );
TryNextMethod();
fi;
- tmp := RUN_IN_GGMBI;
- RUN_IN_GGMBI:=true;
+ PushOptions( rec( Run_In_GGMBI:= true ) );
nice:=RestrictedNiceMonomorphism(G);
geni:=List(gens,i->ImageElm(nice,i));
map2:=GroupGeneralMappingByImagesNC(NiceObject(G),H,geni,imgs);
- RUN_IN_GGMBI:=tmp;
+ PopOptions();
return CompositionMapping(map2,nice);
end );
@@ -956,38 +962,52 @@ InstallMethod( AsGroupGeneralMappingByImages,
[IsGroupGeneralMapping and IsNiceMonomorphism],
{} -> RankFilter( IsHandledByNiceMonomorphism ),
function(hom)
-local h, tmp;
- # we actually want to use the next method with `RUN_IN_GGMBI' set to
+ # we actually want to use the next method with `Run_In_GGMBI' set to
# `true'. Therefore we redispatch, but will skip this method the second
# time.
- if RUN_IN_GGMBI=true then
+ if ValueOption( "Run_In_GGMBI" ) = true then
+ TryNextMethod();
+ elif RUN_IN_GGMBI = true then
+ # Code was called that does not know about the global option.
+ # Make it work but print a warning.
+ Info( InfoWarning, 1,
+ "use the global option 'Run_In_GGMBI' not the global variable ",
+ "'RUN_IN_GGMBI', see '?Run_In_GGMBI'" );
TryNextMethod();
fi;
- tmp := RUN_IN_GGMBI;
- RUN_IN_GGMBI:=true;
- h:=AsGroupGeneralMappingByImages(hom);
- RUN_IN_GGMBI:=tmp;
- return h;
+ return AsGroupGeneralMappingByImages( hom : Run_In_GGMBI:= true );
end);
#############################################################################
##
+#M PreImagesRepresentativeNC( , ) . . . . . . . . . . via images
#M PreImagesRepresentative( , ) . . . . . . . . . . . via images
##
-InstallMethod( PreImagesRepresentative, "for PBG-Niceo",
+InstallMethod( PreImagesRepresentativeNC, "for PBG-Niceo",
FamRangeEqFamElm,
[ IsPreimagesByAsGroupGeneralMappingByImages and IsNiceMonomorphism,
IsMultiplicativeElementWithInverse ], 0,
function( hom, elm )
-local p, tmp;
+local p;
# avoid the double dispatch for `AsGroupGeneralMappingByImages'
tmp := RUN_IN_GGMBI;
RUN_IN_GGMBI:=true;
- p:=PreImagesRepresentative( AsGroupGeneralMappingByImages( hom ), elm );
+ p:=PreImagesRepresentativeNC( AsGroupGeneralMappingByImages( hom ), elm );
RUN_IN_GGMBI:=tmp;
return p;
end );
+InstallMethod( PreImagesRepresentative, "for PBG-Niceo",
+ FamRangeEqFamElm,
+ [ IsPreimagesByAsGroupGeneralMappingByImages and IsNiceMonomorphism,
+ IsMultiplicativeElementWithInverse ], 0,
+function( hom, elm )
+ if not ( elm in Range(hom) ) then
+ return fail;
+ fi;
+ return PreImagesRepresentativeNC( hom, elm );
+end );
+
#############################################################################
##
#M NiceMonomorphism( ) . .
@@ -1078,7 +1098,7 @@ InstallMethod( \[\],"enum-by-niceo", true,
function( enum, pos )
local img;
img:=enum!.niceEnumerator[pos];
- return PreImagesRepresentative(enum!.morphism,img);
+ return PreImagesRepresentativeNC(enum!.morphism,img);
end);
diff --git a/lib/grppc.gi b/lib/grppc.gi
index f01a7af92d..9233d045e2 100644
--- a/lib/grppc.gi
+++ b/lib/grppc.gi
@@ -2147,7 +2147,7 @@ local e, # EAS
if iso<>false then
V:=PreImage(iso,V);
no:=PreImage(iso,no);
- ce:=PreImagesRepresentative(iso,ce);
+ ce:=PreImagesRepresentativeNC(iso,ce);
fi;
return [V,no,ce];
end );
@@ -2568,7 +2568,7 @@ local q, pcgs, sub, hom, f, ex, C;
ex:=ExponentOfPGroupAndElm(f,q);
while ex[1]>q do
# take the element of highest order in f and take power of its preimage
- ex:=PreImagesRepresentative(hom,ex[2]^q);
+ ex:=PreImagesRepresentativeNC(hom,ex[2]^q);
sub:=NormalClosure(G,ClosureSubgroupNC(sub,ex));
hom:=NaturalHomomorphismByNormalSubgroup(G,sub);
f:=Range(hom);
@@ -2646,7 +2646,7 @@ function(G,p,e)
local f;
f:=MaximalAbelianQuotient(G);
IsAbelian(Image(f));
- return SubgroupByPcgs(G,Pcgs(PreImagesSet(f,Omega(Image(f),p,e))));
+ return SubgroupByPcgs(G,Pcgs(PreImagesSetNC(f,Omega(Image(f),p,e))));
end);
# Efficiency notes:
@@ -2679,7 +2679,7 @@ local z,f;
f:=NaturalHomomorphismByNormalSubgroup(G,Subgroup(G,[z]));
IsAbelian(Image(f)); # Probably is not, but quick to check
- return SubgroupByPcgs(G,Pcgs(PreImagesSet(f,Omega(Image(f),p,e))));
+ return SubgroupByPcgs(G,Pcgs(PreImagesSetNC(f,Omega(Image(f),p,e))));
end);
# Efficiency Points:
@@ -2820,7 +2820,7 @@ InstallMethod (HallSubgroupOp, "via IsomoprhismPcGroup", true,
function (grp, pi)
local iso;
iso := IsomorphismPcGroup (grp);
- return PreImagesSet (iso, HallSubgroup (ImagesSource (iso), pi));
+ return PreImagesSetNC(iso, HallSubgroup (ImagesSource (iso), pi));
end);
@@ -2841,7 +2841,7 @@ InstallMethod (SylowComplementOp, "via IsomoprhismPcGroup", true,
function (grp, p)
local iso;
iso := IsomorphismPcGroup (grp);
- return PreImagesSet (iso, SylowComplement (ImagesSource (iso), p));
+ return PreImagesSetNC(iso, SylowComplement (ImagesSource (iso), p));
end);
diff --git a/lib/grppcaut.gi b/lib/grppcaut.gi
index 2840694725..eb3e7a5f51 100644
--- a/lib/grppcaut.gi
+++ b/lib/grppcaut.gi
@@ -437,7 +437,7 @@ local spec,s,n,M,
if d = 1 then
hom := IsomorphismPermGroup( B );
pcgs := Pcgs( Image( hom ) );
- pcs := List( pcgs, x -> PreImagesRepresentative( hom, x ) );
+ pcs := List( pcgs, x -> PreImagesRepresentativeNC( hom, x ) );
TransferPcgsInfo( B, pcs, RelativeOrders( pcgs ) );
return B;
fi;
@@ -509,12 +509,12 @@ local spec,s,n,M,
Info( InfoOverGr, 1, "computed normalizer of size ", Size(L));
# go back to mat group
- B := List( GeneratorsOfGroup(L), x -> PreImagesRepresentative(hom,x) );
+ B := List( GeneratorsOfGroup(L), x -> PreImagesRepresentativeNC(hom,x) );
w := PrimitiveRoot(field)* Immutable( IdentityMat( d, field ) );
B := SubgroupNC( S, Concatenation( B, [w] ) );
if IsSolvableGroup( L ) then
- pcgs := List( Pcgs(L), x -> PreImagesRepresentative( hom, x ) );
+ pcgs := List( Pcgs(L), x -> PreImagesRepresentativeNC( hom, x ) );
Add( pcgs, w );
rels := ShallowCopy( RelativeOrders( Pcgs(L) ) );
Add( rels, p-1 );
@@ -536,7 +536,7 @@ BindGlobal( "CocycleSQ", function( epi, field )
H := Source( epi );
F := Image( epi );
N := KernelOfMultiplicativeGeneralMapping( epi );
- pcsH := List( Pcgs( F ), x -> PreImagesRepresentative( epi, x ) );
+ pcsH := List( Pcgs( F ), x -> PreImagesRepresentativeNC( epi, x ) );
pcsN := Pcgs( N );
pcgsH := PcgsByPcSequence( ElementsFamily( FamilyObj( H ) ),
Concatenation( pcsH, pcsN ) );
@@ -646,7 +646,7 @@ BindGlobal( "LiftInduciblePair", function( epi, ind, M, weight )
pcgsF := Pcgs( F );
- pcsH := List( pcgsF, x -> PreImagesRepresentative( epi, x ) );
+ pcsH := List( pcgsF, x -> PreImagesRepresentativeNC( epi, x ) );
pcsN := Pcgs( N );
pcgsH := PcgsByPcSequence( ElementsFamily( FamilyObj( H ) ),
Concatenation( pcsH, pcsN ) );
@@ -656,7 +656,7 @@ BindGlobal( "LiftInduciblePair", function( epi, ind, M, weight )
# use automorphism of F
imgsF := List( pcgsF, x -> Image( ind[1], x ) );
opmats := List( imgsF, x -> MappedPcElement( x, pcgsF, M.generators ) );
- imgsF := List( imgsF, x -> PreImagesRepresentative( epi, x ) );
+ imgsF := List( imgsF, x -> PreImagesRepresentativeNC( epi, x ) );
# use automorphism of N
imgsN := List( pcsN, x -> ExponentsOfPcElement( pcsN, x ) );
@@ -1418,11 +1418,11 @@ InstallGlobalFunction(AutomorphismGroupSolvableGroup,function( G )
hom := ActionHomomorphism( xset, "surjective");
P := Image( hom );
if IsSolvableGroup( P ) then
- pcsA := List( Pcgs(P), x -> PreImagesRepresentative( hom, x ));
+ pcsA := List( Pcgs(P), x -> PreImagesRepresentativeNC( hom, x ));
TransferPcgsInfo( A, pcsA, RelativeOrders( Pcgs(P) ) );
else
imgs := SmallGeneratingSet( P );
- gens := List( imgs, x -> PreImagesRepresentative( hom, x ) );
+ gens := List( imgs, x -> PreImagesRepresentativeNC( hom, x ) );
tmp := Size( A );
A := GroupByGenerators( gens, One( A ) );
SetSize( A, tmp );
@@ -1543,10 +1543,10 @@ InstallGlobalFunction(AutomorphismGroupFrattFreeGroup,function( G )
imgs := [];
for i in [1..Length(gensK)] do
m := gensU[i]^n;
- a := PreImagesRepresentative( hom, m );
+ a := PreImagesRepresentativeNC( hom, m );
Add( imgs, a );
od;
- l := PreImagesRepresentative( iso, n );
+ l := PreImagesRepresentativeNC( iso, n );
Append( imgs, List( gensF, x -> Image( l, x ) ) );
new := GroupHomomorphismByImagesNC( G, G, gensG, imgs );
SetIsBijective( new, true );
diff --git a/lib/grppccom.gi b/lib/grppccom.gi
index 2dc5682575..bb59eef42e 100644
--- a/lib/grppccom.gi
+++ b/lib/grppccom.gi
@@ -19,7 +19,7 @@ local r,img,i,gens,img2;
gens:=GeneratorsOfGroup(img);
img2:=Image(h[i],G);
r[i]:=GroupHomomorphismByImagesNC(img,img2,gens,List(gens,j->
- Image(h[i],PreImagesRepresentative(h[i+1],j))));
+ Image(h[i],PreImagesRepresentativeNC(h[i+1],j))));
SetKernelOfMultiplicativeGeneralMapping(r[i],
Image(h[i+1],KernelOfMultiplicativeGeneralMapping(h[i])));
img:=img2;
@@ -890,7 +890,7 @@ local H, E, cor, a, i, fun2,pcgs,home;
#a :=NaturalHomomorphism( G, G / N );
#cor:=PPrimeSetsOC( Image( a ) );
#cor.generators:=List( cor.generators, x ->
- # PreImagesRepresentative( a, x ) );
+ # PreImagesRepresentativeNC( a, x ) );
cor:=rec(home:=home,generators:=pcgs mod InducedPcgs(pcgs,N));
cor.useCentralSK:=true;
fi;
diff --git a/lib/grppcext.gi b/lib/grppcext.gi
index 4cfb4063a1..bcc5e554a9 100644
--- a/lib/grppcext.gi
+++ b/lib/grppcext.gi
@@ -378,11 +378,11 @@ local ag, p1iso, agp, p2iso, DP, p1, p2, gens, genimgs, triso,s,i,u,opt,
genimgs:=List(gens,
i->ImagesRepresentative(Embedding(D,1),
- PreImagesRepresentative(p1iso,
- PreImagesRepresentative(pc1,ImagesRepresentative(p1,i))))
+ PreImagesRepresentativeNC(p1iso,
+ PreImagesRepresentativeNC(pc1,ImagesRepresentative(p1,i))))
*ImagesRepresentative(Embedding(D,2),
- PreImagesRepresentative(p2iso,
- PreImagesRepresentative(pc2,ImagesRepresentative(p2,i)))) );
+ PreImagesRepresentativeNC(p2iso,
+ PreImagesRepresentativeNC(pc2,ImagesRepresentative(p2,i)))) );
else
opt:=rec(limit:=s,random:=1);
@@ -426,9 +426,9 @@ local ag, p1iso, agp, p2iso, DP, p1, p2, gens, genimgs, triso,s,i,u,opt,
genimgs:=List(gens,
i->ImagesRepresentative(Embedding(D,1),
- PreImagesRepresentative(p1iso,ImagesRepresentative(p1,i)))
+ PreImagesRepresentativeNC(p1iso,ImagesRepresentative(p1,i)))
*ImagesRepresentative(Embedding(D,2),
- PreImagesRepresentative(p2iso,ImagesRepresentative(p2,i))) );
+ PreImagesRepresentativeNC(p2iso,ImagesRepresentative(p2,i))) );
fi;
triso:=GroupHomomorphismByImagesNC(DP,D,gens,genimgs);
@@ -528,7 +528,7 @@ local G, M, Mgrp, oper, A, B, D, translate, gens, genimgs, triso, K, K1,
gens,M.generators);
test:=function(perm)
local aut,imgs,mat;
- aut:=PreImagesRepresentative(triso,perm);
+ aut:=PreImagesRepresentativeNC(triso,perm);
imgs:=List(gens,x->ImagesRepresentative(aut,x));
imgs:=List(imgs,x->ImagesRepresentative(modulehom,x));
mat:=MTX.IsomorphismModules(M,GModuleByMats(imgs,M.field));
@@ -696,9 +696,9 @@ local G, M, Mgrp, oper, A, B, D, translate, gens, genimgs, triso, K, K1,
basicact:=function( tup, elm )
local gens;
- #gens := List( tup[1], x -> PreImagesRepresentative( elm[1], x ) );
+ #gens := List( tup[1], x -> PreImagesRepresentativeNC( elm[1], x ) );
#gens := List( gens, x -> MappedPcElement( x, tup[1], tup[2] ) );
- gens := List( Ggens, x -> PreImagesRepresentative( elm[1], x ) );
+ gens := List( Ggens, x -> PreImagesRepresentativeNC( elm[1], x ) );
gens := List( gens, x -> MappedPcElement( x, Ggens, tup ) );
gens := List( gens, x -> x ^ elm[2] );
return gens;
@@ -711,10 +711,10 @@ local G, M, Mgrp, oper, A, B, D, translate, gens, genimgs, triso, K, K1,
Assert(1,MappingGeneratorsImages(epi)[2]=Ggens);
f:=function( tup, elm )
local gens;
- #gens := List( tup[1], x -> PreImagesRepresentative( elm[1], x ) );
+ #gens := List( tup[1], x -> PreImagesRepresentativeNC( elm[1], x ) );
#gens := List( gens, x -> MappedPcElement( x, tup[1], tup[2] ) );
- gens := List( Ggens, x -> PreImagesRepresentative( elm[1], x ) );
- gens := List( gens, x -> MappedWord( PreImagesRepresentative(epi,x),
+ gens := List( Ggens, x -> PreImagesRepresentativeNC( elm[1], x ) );
+ gens := List( gens, x -> MappedWord( PreImagesRepresentativeNC(epi,x),
GeneratorsOfGroup(Source(epi)), tup ) );
gens := List( gens, x -> x ^ elm[2] );
return gens;
@@ -730,13 +730,13 @@ local G, M, Mgrp, oper, A, B, D, translate, gens, genimgs, triso, K, K1,
elmlist:=[];
tmp:=List(genimgs,x->x[1]);
- preimlist:=List(tmp,x->[x,List(Ggens,y->PreImagesRepresentative(x,y))]);
+ preimlist:=List(tmp,x->[x,List(Ggens,y->PreImagesRepresentativeNC(x,y))]);
f:=function( tup, elm )
local gens,p;
p:=PositionProperty(preimlist,x->IsIdenticalObj(x[1],elm[1]));
if p=fail then
- gens := List( Ggens, x -> PreImagesRepresentative( elm[1], x ) );
+ gens := List( Ggens, x -> PreImagesRepresentativeNC( elm[1], x ) );
else
gens:=preimlist[p][2];
fi;
@@ -781,7 +781,7 @@ local G, M, Mgrp, oper, A, B, D, translate, gens, genimgs, triso, K, K1,
if elmlist<>fail then
tmp:=List(genimgs,x->x[1]);
- preimlist:=List(tmp,x->[x,List(Ggens,y->PreImagesRepresentative(x,y))]);
+ preimlist:=List(tmp,x->[x,List(Ggens,y->PreImagesRepresentativeNC(x,y))]);
# ensure we also account for action
u:=Group(tup);
@@ -911,7 +911,7 @@ BindGlobal( "MatrixOperationOfCPGroup", function( cc, gens )
mats := List( gens, x -> [] );
base := Basis( Image( cc.cohom ) );
- prei := List( base, x -> PreImagesRepresentative( cc.cohom, x ) );
+ prei := List( base, x -> PreImagesRepresentativeNC( cc.cohom, x ) );
pcgs := Pcgs( cc.group );
ords := RelativeOrders( pcgs );
@@ -1008,7 +1008,7 @@ function( G, M, C )
return [ExtensionSQ( cc.collector, G, M, 0 )];
elif Dimension( Image(cc.cohom)) = 1 then
c := Basis(Image(cc.cohom))[1];
- c := PreImagesRepresentative(cc.cohom, c);
+ c := PreImagesRepresentativeNC(cc.cohom, c);
return [ExtensionSQ( cc.collector, G, M, 0 ),
ExtensionSQ( cc.collector, G, M, c )];
fi;
@@ -1018,7 +1018,7 @@ function( G, M, C )
# compute orbit of mats on H^2( G, M )
Mgrp := GroupByGenerators( mats );
orbs := OrbitsDomain( Mgrp, Image(cc.cohom), OnRight );
- orbs := List( orbs, x -> PreImagesRepresentative( cc.cohom, x[1] ) );
+ orbs := List( orbs, x -> PreImagesRepresentativeNC( cc.cohom, x[1] ) );
ext := List( orbs, x -> ExtensionSQ( cc.collector, G, M, x ) );
return ext;
end);
@@ -1113,7 +1113,7 @@ BindGlobal( "NonSplitExtensions", function( arg )
red := true;
elif Dimension( Image(cc.cohom ) ) = 1 then
- c := PreImagesRepresentative(cc.cohom, Basis(Image(cc.cohom))[1]);
+ c := PreImagesRepresentativeNC(cc.cohom, Basis(Image(cc.cohom))[1]);
all := [ExtensionSQ( C, G, M, c)];
red := true;
@@ -1121,7 +1121,7 @@ BindGlobal( "NonSplitExtensions", function( arg )
elif IsBound( arg[3] ) and not arg[3] then
all := NormedRowVectors( Image(cc.cohom) );
all := List( all, x -> ExtensionSQ(cohom.collector, G, M,
- PreImagesRepresentative(cc.cohom,x )));
+ PreImagesRepresentativeNC(cc.cohom,x )));
red := false;
# sometimes we do not want to reduce
@@ -1132,7 +1132,7 @@ BindGlobal( "NonSplitExtensions", function( arg )
then
all := NormedRowVectors( Image(cc.cohom) );
all := List( all, x -> ExtensionSQ(cc.collector, G, M,
- PreImagesRepresentative(cc.cohom, x )));
+ PreImagesRepresentativeNC(cc.cohom, x )));
red := false;
# then we want to reduce
@@ -1151,7 +1151,7 @@ BindGlobal( "NonSplitExtensions", function( arg )
# create extensions and add info
all := List( all, x -> ExtensionSQ(cc.collector, G, M,
- PreImagesRepresentative(cc.cohom, x )));
+ PreImagesRepresentativeNC(cc.cohom, x )));
fi;
if red then
diff --git a/lib/grppclat.gi b/lib/grppclat.gi
index 4b8113783e..b313ba6359 100644
--- a/lib/grppclat.gi
+++ b/lib/grppclat.gi
@@ -86,7 +86,7 @@ local f;
else
aut:= GroupHomomorphismByImagesNC(f,f,GeneratorsOfGroup(f),
List(GeneratorsOfGroup(f),
- i->Image(epi,Image(aut,PreImagesRepresentative(epi,i)))));
+ i->Image(epi,Image(aut,PreImagesRepresentativeNC(epi,i)))));
SetIsInjective(aut,true);
SetIsSurjective(aut,true);
fi;
@@ -672,7 +672,7 @@ local g, # group
# hom:=[];
# for i in func do
# hom2:=GroupHomomorphismByImagesNC(g,g,g.generators,List(g.generators,
-# j->Image(isom,Image(i,PreImagesRepresentative(isom,j)))));
+# j->Image(isom,Image(i,PreImagesRepresentativeNC(isom,j)))));
# hom2.isMapping:=true;
# Add(hom,hom2);
# od;
@@ -788,7 +788,7 @@ local g, # group
hom:= GroupHomomorphismByImagesNC(f,fa,GeneratorsOfGroup(f),
List(GeneratorsOfGroup(f),i->
- Image(hom,PreImagesRepresentative(epi,i))));
+ Image(hom,PreImagesRepresentativeNC(epi,i))));
Assert(2,KernelOfMultiplicativeGeneralMapping(hom)=n);
# lift the known groups
diff --git a/lib/grpperm.gi b/lib/grpperm.gi
index 020398dfe5..08f7805298 100644
--- a/lib/grpperm.gi
+++ b/lib/grpperm.gi
@@ -1592,7 +1592,7 @@ InstallGlobalFunction( SylowSubgroupPermGroup, function( G, p )
O := Orbit( S, D[1] );
f := ActionHomomorphism( S, O,"surjective" );
T := SylowSubgroupPermGroup( Range( f ), p );
- S := PreImagesSet( f, T );
+ S := PreImagesSetNC( f, T );
SubtractSet( D, O );
od;
return S;
@@ -1605,7 +1605,7 @@ InstallGlobalFunction( SylowSubgroupPermGroup, function( G, p )
f := ActionHomomorphism( G, B, OnSets,"surjective" );
T := SylowSubgroupPermGroup( Range( f ), p );
if Size( T ) < Size( Range( f ) ) then
- T := PreImagesSet( f, T );
+ T := PreImagesSetNC( f, T );
S := SylowSubgroupPermGroup( T , p) ;
return S;
fi;
@@ -1630,7 +1630,7 @@ InstallGlobalFunction( SylowSubgroupPermGroup, function( G, p )
Info(InfoGroup,1,"PermSylow: cycleaction");
f := ActionHomomorphism( C, B, OnSets,"surjective" );
T := SylowSubgroupPermGroup( Range( f ), p );
- S := PreImagesSet( f, T );
+ S := PreImagesSetNC( f, T );
return S;
end );
diff --git a/lib/grpprmcs.gi b/lib/grpprmcs.gi
index c8a8a1166a..8ba3001d28 100644
--- a/lib/grpprmcs.gi
+++ b/lib/grpprmcs.gi
@@ -1173,7 +1173,7 @@ InstallGlobalFunction( PullbackKernelCSPG,
fi;
for g in gens do
for j in [1..i-1] do
- g := PreImagesRepresentative(homlist[i-j],g);
+ g := PreImagesRepresentativeNC(homlist[i-j],g);
od;
Add(normals[index],g);
Add(factors[index],());
@@ -1193,7 +1193,7 @@ InstallGlobalFunction( PullbackCSPG, function(p,homlist)
# compute a preimage of the permutation p in the input group
lenhomlist := Length(homlist);
for i in [1..lenhomlist] do
- p := PreImagesRepresentative(homlist[lenhomlist+1-i],p);
+ p := PreImagesRepresentativeNC(homlist[lenhomlist+1-i],p);
od;
return p;
end );
@@ -1522,7 +1522,7 @@ InstallMethod( PCoreOp,
for g in GeneratorsOfGroup( KernelOfMultiplicativeGeneralMapping(
homlist[i] ) ) do
for j in [1..i-1] do
- g := PreImagesRepresentative(homlist[i-j],g);
+ g := PreImagesRepresentativeNC(homlist[i-j],g);
od;
Add(pgenlist,g);
od;
@@ -1747,7 +1747,7 @@ InstallMethod( SolvableRadical,
for g in GeneratorsOfGroup( KernelOfMultiplicativeGeneralMapping(
homlist[i] ) ) do
for j in [1..i-1] do
- g := PreImagesRepresentative(homlist[i-j],g);
+ g := PreImagesRepresentativeNC(homlist[i-j],g);
od;
Add(solvable,g);
od;
@@ -1873,7 +1873,7 @@ InstallMethod( Centre,
else
order := Size( centr );
cent := IntersectionNormalClosurePermGroup(GG,centr,order*Size(GG));
- cent:= PreImages(tchom,cent);
+ cent:= PreImagesNC(tchom,cent);
Assert( 1, IsAbelian( cent ) );
SetIsAbelian( cent, true );
return cent;
@@ -1917,7 +1917,7 @@ InstallMethod( Centre,
cent := IntersectionNormalClosurePermGroup
( GG, GroupByGenerators(hgens,()), order*Size(GG) );
if n <> len then
- cent:= PreImages( tchom, cent );
+ cent:= PreImagesNC( tchom, cent );
fi;
Assert( 1, IsAbelian( cent ) );
SetIsAbelian( cent, true );
@@ -2012,7 +2012,7 @@ InstallGlobalFunction( CentralizerNormalCSPG, function(G,N)
# handle case of transitive GG directly
if Length(significant) = 1 then
centrnorm := CentralizerNormalTransCSPG(GG,NN);
- return PreImages(tchom,centrnorm);
+ return PreImagesNC(tchom,centrnorm);
fi;
# case of intransitive GG
@@ -2054,7 +2054,7 @@ InstallGlobalFunction( CentralizerNormalCSPG, function(G,N)
if n = len then
return central;
else
- return PreImages(tchom,central);
+ return PreImagesNC(tchom,central);
fi;
end );
diff --git a/lib/info.gi b/lib/info.gi
index 7436dfa86b..7c873f9661 100644
--- a/lib/info.gi
+++ b/lib/info.gi
@@ -45,11 +45,7 @@
DeclareRepresentation("IsInfoClassListRep", IsAtomicPositionalObjectRep);
# A list of all created InfoClassListReps
-INFO_CLASSES := [];
-
-# InfoData is unused, but we keep it for now, to avoid warnings in GAPDoc.
-# TODO: remove InfoData
-InfoData := rec();
+BIND_GLOBAL( "INFO_CLASSES", [] );
if IsHPCGAP then
ShareInternalObj(INFO_CLASSES);
diff --git a/lib/init.g b/lib/init.g
index 03601c810a..f6061f1e58 100644
--- a/lib/init.g
+++ b/lib/init.g
@@ -34,8 +34,8 @@ OnBreak := function() Print("An error has occurred before the traceback ",
## break loop.
##
OnBreakMessage := function()
- Print("you can 'quit;' to quit to outer loop, or\n",
- "you can 'return;' to continue\n");
+ Print("you can enter 'quit;' to quit to outer loop, or\n",
+ "you can enter 'return;' to continue\n");
end;
#############################################################################
@@ -434,7 +434,7 @@ function( prefix, values, suffix )
end);
BindGlobal( "ShowKernelInformation", function()
- local sysdate, btop, vert, bbot, config, str, gap;
+ local sysdate, btop, bmid, bbot, config, str, gap;
if GAPInfo.Date <> "today" then
sysdate := " of ";
@@ -447,19 +447,23 @@ BindGlobal( "ShowKernelInformation", function()
fi;
if GAPInfo.TermEncoding = "UTF-8" then
- btop := "┌───────┐\c"; vert := "│"; bbot := "└───────┘\c";
+ btop := " ● G";
+ bmid := "● ● A";
+ bbot := " ● P";
else
- btop := "*********"; vert := "*"; bbot := btop;
+ btop := " o G";
+ bmid := "o o A";
+ bbot := " o P";
fi;
if IsHPCGAP then
gap := "HPC-GAP";
else
gap := "GAP";
fi;
- Print( " ",btop," ",gap," ", GAPInfo.BuildVersion,
+ Print( " ",btop," ",gap," ", GAPInfo.BuildVersion,
sysdate, "\n",
- " ",vert," GAP ",vert," https://www.gap-system.org\n",
- " ",bbot," Architecture: ", GAPInfo.Architecture, "\n" );
+ " ",bmid," https://www.gap-system.org\n",
+ " ",bbot," Architecture: ", GAPInfo.Architecture, "\n" );
if IsHPCGAP then
Print( " Maximum concurrent threads: ",
GAPInfo.KernelInfo.NUM_CPUS, "\n");
diff --git a/lib/integer.gd b/lib/integer.gd
index 20ca4e07ed..29be88cae8 100644
--- a/lib/integer.gd
+++ b/lib/integer.gd
@@ -249,12 +249,13 @@ DeclareGlobalFunction( "BestQuoInt" );
## ChineseRem( [ 6, 10, 14 ], [ 1, 2, 3 ] );
## Error, the residues must be equal modulo 2
+## Stack trace:
## *[1] Error( "the residues must be equal modulo ", g.gcd );
## @ GAPROOT/lib/integer.gi:391
## ( )
## called from read-eval loop at *stdin*:2
-## you can 'quit;' to quit to outer loop, or
-## you can 'return;' to continue
+## you can enter 'quit;' to quit to outer loop, or
+## you can enter 'return;' to continue
## brk>
## ]]>
##
diff --git a/lib/integer.gi b/lib/integer.gi
index b5da9421d7..9928ff6cb3 100644
--- a/lib/integer.gi
+++ b/lib/integer.gi
@@ -727,7 +727,7 @@ InstallGlobalFunction(FactorsInt,function ( n )
return Factors(n_orig);
else
Error( "sorry, cannot factor ", tmp[2],
- "\ntype 'return;' to try again with a larger number of trials in\n",
+ "\nyou can enter 'return;' to try again with a larger number of trials in\n",
"FactorsRho (or use option 'RhoTrials')\n");
if ValueOption("RhoTrials") <> fail then
rt := 5 * ValueOption("RhoTrials");
diff --git a/lib/liefam.gi b/lib/liefam.gi
index 6122a753b0..0f9f70c53f 100644
--- a/lib/liefam.gi
+++ b/lib/liefam.gi
@@ -447,7 +447,7 @@ InstallMethod( ImagesElm,
return [ LieObject( elm ) ];
end );
-InstallMethod( PreImagesElm,
+InstallMethod( PreImagesElmNC,
"for Lie embedding and Lie object in default representation",
FamRangeEqFamElm,
[ IsGeneralMapping and IsLieEmbeddingRep,
@@ -456,6 +456,17 @@ InstallMethod( PreImagesElm,
return [ elm![1] ];
end );
+InstallMethod( PreImagesElm,
+ "for Lie embedding and Lie object in default representation",
+ FamRangeEqFamElm,
+ [ IsGeneralMapping and IsLieEmbeddingRep,
+ IsLieObject and IsPackedElementDefaultRep ], 0,
+ function( emb, elm )
+ if not ( elm in Range(emb) ) then
+ return fail;
+ fi;
+ return PreImagesElm( emb, elm );
+ end );
#############################################################################
##
diff --git a/lib/list.gd b/lib/list.gd
index 5a44805bae..f595715899 100644
--- a/lib/list.gd
+++ b/lib/list.gd
@@ -379,7 +379,7 @@ DeclareSynonym( "AsSSortedListList", AS_LIST_SORTED_LIST );
## Lists with holes are sometimes convenient when the list represents
## a mapping from a finite, but not consecutive,
## subset of the positive integers.
-## IsDenseList( [ 1, 2, 3 ] );
## true
## gap> l := [ , 4, 9,, 25,, 49,,,, 121 ];; IsDenseList( l );
@@ -387,22 +387,12 @@ DeclareSynonym( "AsSSortedListList", AS_LIST_SORTED_LIST );
## gap> l[3];
## 9
## gap> l[4];
-## List Element: [4] must have an assigned value
-## not in any function
-## Entering break read-eval-print loop ...
-## you can 'quit;' to quit to outer loop, or
-## you can 'return;' after assigning a value to continue
-## brk> l[4] := 16;; # assigning a value
-## brk> return; # to escape the break-loop
-## 16
-## gap>
-## ]]>
+## Error, List Element: [4] must have an assigned value
+## ]]>
##
## Observe that requesting the value of l[4], which was not
## assigned, caused the entry of a break-loop
## (see Section ).
-## After assigning a value and typing return;, &GAP; is finally
-## able to comply with our request (by responding with 16).
##
##
## <#/GAPDoc>
diff --git a/lib/mapphomo.gi b/lib/mapphomo.gi
index 3e396945ff..fbd38cb004 100644
--- a/lib/mapphomo.gi
+++ b/lib/mapphomo.gi
@@ -330,9 +330,9 @@ InstallMethod( ImagesSet,
#############################################################################
##
-#M PreImagesElm( , ) . for s.p. gen. mapping resp. mult. & inv.
+#M PreImagesElmNC( , ) . for s.p. gen. mapping resp. mult. & inv.
##
-InstallMethod( PreImagesElm,
+InstallMethod( PreImagesElmNC,
"method for s.p. general mapping respecting mult. & inv., and element",
FamRangeEqFamElm,
[ IsSPGeneralMapping and RespectsMultiplication and RespectsInverses,
@@ -340,7 +340,7 @@ InstallMethod( PreImagesElm,
function( map, elm )
local pre;
- pre:= PreImagesRepresentative( map, elm );
+ pre:= PreImagesRepresentativeNC( map, elm );
if pre = fail then
return [];
else
@@ -351,9 +351,9 @@ InstallMethod( PreImagesElm,
#############################################################################
##
-#M PreImagesSet( , ) . for s.p. gen. mapping resp. mult. & inv.
+#M PreImagesSetNC( , ) . for s.p. gen. mapping resp. mult. & inv.
##
-InstallMethod( PreImagesSet,
+InstallMethod( PreImagesSetNC,
"method for s.p. general mapping respecting mult. & inv., and group",
CollFamRangeEqFamElms,
[ IsSPGeneralMapping and RespectsMultiplication and RespectsInverses,
@@ -367,7 +367,7 @@ InstallMethod( PreImagesSet,
fi;
genpreimages:= List(genpreimages,
- gen -> PreImagesRepresentative( map, gen ) );
+ gen -> PreImagesRepresentativeNC( map, gen ) );
if fail in genpreimages then
TryNextMethod();
fi;
@@ -384,7 +384,7 @@ InstallMethod( PreImagesSet,
return pre;
end );
-InstallMethod( PreImagesSet,
+InstallMethod( PreImagesSetNC,
"method for injective s.p. mapping respecting mult. & inv., and group",
CollFamRangeEqFamElms,
[ IsSPGeneralMapping and IsMapping and IsInjective and
@@ -395,7 +395,7 @@ InstallMethod( PreImagesSet,
pre := SubgroupNC( Source( map ),
List( GeneratorsOfMagmaWithInverses( elms ),
- gen -> PreImagesRepresentative( map, gen ) ) );
+ gen -> PreImagesRepresentativeNC( map, gen ) ) );
UseIsomorphismRelation( elms, pre );
return pre;
end );
@@ -684,9 +684,9 @@ InstallMethod( ImagesSet,
#############################################################################
##
-#M PreImagesElm( , ) for s.p. gen. mapping resp. add. & add.inv.
+#M PreImagesElmNC( , ) for s.p. gen. mapping resp. add. & add.inv.
##
-InstallMethod( PreImagesElm,
+InstallMethod( PreImagesElmNC,
"method for s.p. gen. mapping respecting add. & add.inv., and element",
FamRangeEqFamElm,
[ IsSPGeneralMapping and RespectsAddition and RespectsAdditiveInverses,
@@ -694,7 +694,7 @@ InstallMethod( PreImagesElm,
function( map, elm )
local pre;
- pre:= PreImagesRepresentative( map, elm );
+ pre:= PreImagesRepresentativeNC( map, elm );
if pre = fail then
return [];
else
@@ -705,9 +705,9 @@ InstallMethod( PreImagesElm,
#############################################################################
##
-#M PreImagesSet( , ) for s.p. gen. mapping resp. add. & add.inv.
+#M PreImagesSetNC( , ) for s.p. gen. mapp. resp. add. & add.inv.
##
-InstallMethod( PreImagesSet,
+InstallMethod( PreImagesSetNC,
"method for s.p. gen. mapping resp. add. & add.inv., and add. group",
CollFamRangeEqFamElms,
[ IsSPGeneralMapping and RespectsAddition and RespectsAdditiveInverses,
@@ -715,7 +715,7 @@ InstallMethod( PreImagesSet,
function( map, elms )
local genpreimages;
genpreimages:= List( GeneratorsOfAdditiveGroup( elms ),
- gen -> PreImagesRepresentative( map, gen ) );
+ gen -> PreImagesRepresentativeNC( map, gen ) );
if fail in genpreimages then
TryNextMethod();
fi;
@@ -890,9 +890,9 @@ InstallMethod( ImagesSet,
#############################################################################
##
-#M PreImagesSet( , ) . . . . for linear mapping and left module
+#M PreImagesSetNC( , ) . . . for linear mapping and left module
##
-InstallMethod( PreImagesSet,
+InstallMethod( PreImagesSetNC,
"method for linear mapping and left module",
CollFamRangeEqFamElms,
[ IsSPGeneralMapping and RespectsAddition and RespectsAdditiveInverses
@@ -901,7 +901,7 @@ InstallMethod( PreImagesSet,
function( map, elms )
local genpreimages;
genpreimages:= List( GeneratorsOfLeftModule( elms ),
- gen -> PreImagesRepresentative( map, gen ) );
+ gen -> PreImagesRepresentativeNC( map, gen ) );
if fail in genpreimages then
TryNextMethod();
fi;
@@ -984,9 +984,9 @@ InstallMethod( ImagesSet,
#############################################################################
##
-#M PreImagesSet( , ) . . . . . . . . for algebra hom. and FLMLOR
+#M PreImagesSetNC( , ) . . . . . . . for algebra hom. and FLMLOR
##
-InstallMethod( PreImagesSet,
+InstallMethod( PreImagesSetNC,
"method for algebra hom. and FLMLOR",
CollFamRangeEqFamElms,
[ IsSPGeneralMapping and RespectsAddition and RespectsAdditiveInverses
@@ -995,7 +995,7 @@ InstallMethod( PreImagesSet,
function( map, elms )
local genpreimages;
genpreimages:= List( GeneratorsOfLeftOperatorRing( elms ),
- gen -> PreImagesRepresentative( map, gen ) );
+ gen -> PreImagesRepresentativeNC( map, gen ) );
if fail in genpreimages then
TryNextMethod();
fi;
@@ -1010,9 +1010,9 @@ InstallMethod( PreImagesSet,
#############################################################################
##
-#M PreImagesSet( , ) for alg.-with-one hom. and FLMLOR-with-one
+#M PreImagesSetNC( , ) for alg-with-one hom. and FLMLOR-with-one
##
-InstallMethod( PreImagesSet,
+InstallMethod( PreImagesSetNC,
"method for algebra-with-one hom. and FLMLOR-with-one",
CollFamRangeEqFamElms,
[ IsSPGeneralMapping and RespectsAddition and RespectsAdditiveInverses
@@ -1022,7 +1022,7 @@ InstallMethod( PreImagesSet,
function( map, elms )
local genpreimages;
genpreimages:= List( GeneratorsOfLeftOperatorRingWithOne( elms ),
- gen -> PreImagesRepresentative( map, gen ) );
+ gen -> PreImagesRepresentativeNC( map, gen ) );
if fail in genpreimages then
TryNextMethod();
fi;
diff --git a/lib/mapping.gd b/lib/mapping.gd
index 12d2ff39dc..2b391b67cb 100644
--- a/lib/mapping.gd
+++ b/lib/mapping.gd
@@ -751,7 +751,7 @@ DeclareAttribute( "ImagesSource", IsGeneralMapping );
##
## is the set of preimages of the range of the general mapping map.
##
-## delegates to ,
+## delegates to ,
## it is introduced only to store the preimage of map as attribute
## value.
##
@@ -968,7 +968,8 @@ DeclareGlobalFunction( "Images" );
#############################################################################
##
-#O PreImagesElm( , ) . all preimages of elm under a gen. mapping
+#O PreImagesElm( , ) . . . . . . . . . . . . all preimages of elm
+#O PreImagesElmNC( , ) . . . . . . . . . . . under a gen. mapping
##
## <#GAPDoc Label="PreImagesElm">
##
@@ -976,16 +977,23 @@ DeclareGlobalFunction( "Images" );
##
##
## If elm is an element of the range of the general mapping
-## map then returns the set of all
+## map then returns the set of all
## preimages of elm under map.
##
-## Anything may happen if elm is not an element of the range of
-## map.
+## From &GAP; version 4.16.0
+## PreImagesElm was renamed PreImagesElmNC
+## throughout the library, and PreImagesElm now checks that
+## elm is an element of the range before calling PreImagesElmNC.
+##
+## When using PreImagesElmNC anything may happen if elm
+## is not an element of the range of map.
+##
##
##
## <#/GAPDoc>
##
DeclareOperation( "PreImagesElm", [ IsGeneralMapping, IsObject ] );
+DeclareOperation( "PreImagesElmNC", [ IsGeneralMapping, IsObject ] );
#############################################################################
@@ -1015,11 +1023,12 @@ DeclareOperation( "PreImageElm",
#############################################################################
##
#O PreImagesRepresentative( , ) . . . one preimage of an element
-## under a gen. mapping
+#O PreImagesRepresentativeNC( , ) . . . . under a general mapping
##
## <#GAPDoc Label="PreImagesRepresentative">
##
##
+##
##
##
## If elm is an element of the range of the general mapping
@@ -1028,36 +1037,51 @@ DeclareOperation( "PreImageElm",
## fail, the latter if and only if elm
## has no preimages under map.
##
-## Anything may happen if elm is not an element of the range of
-## map.
+## From &GAP; version 4.16.0 PreImagesRepresentative
+## was renamed PreImagesRepresentativeNC throughout the library,
+## and PreImagesRepresentative now checks that elm is an
+## element of the range before calling PreImagesRepresentativeNC.
+##
+## When using PreImagesRepresentativeNC anything may happen if
+## elm is not an element of the range of map.
+##
##
##
## <#/GAPDoc>
##
-DeclareOperation( "PreImagesRepresentative",
- [ IsGeneralMapping, IsObject ] );
+DeclareOperation( "PreImagesRepresentative", [ IsGeneralMapping, IsObject ] );
+DeclareOperation( "PreImagesRepresentativeNC", [ IsGeneralMapping, IsObject ] );
#############################################################################
##
#O PreImagesSet( , )
+#O PreImagesSetNC( , )
##
## <#GAPDoc Label="PreImagesSet">
##
##
+##
##
##
## If elms is a subset of the range of the general mapping map
## then returns the set of all preimages of
## elms under map.
##
-## Anything may happen if elms is not a subset of the range of
-## map.
+## From &GAP; version 4.16.0 PreImagesSet
+## has been renamed PreImagesSetNC throughout the library,
+## and PreImagesSet now checks that elms is a
+## subset of the range before calling PreImagesSetNC.
+##
+## When using PreImagesSetNC anything may happen if elms
+## is not a subset of the range of map.
+##
##
##
## <#/GAPDoc>
##
DeclareOperation( "PreImagesSet", [ IsGeneralMapping, IsListOrCollection ] );
+DeclareOperation( "PreImagesSetNC", [ IsGeneralMapping, IsListOrCollection ] );
#############################################################################
@@ -1119,18 +1143,27 @@ DeclareGlobalFunction( "PreImage" );
#############################################################################
##
#F PreImages( ) . . . set of preimages of the range of a gen. mapping
+#F PreImagesNC( ) . . set of preimages of the range of a gen. mapping
#F PreImages(,) . set of preimages of an elm under a gen. mapping
-#F PreImages(,) set of preimages of a coll. under a gen. mapping
+#F PreImagesNC(,) set of preimages of an elm under a gen. mapping
+#F PreImages(,) set of preimages of a coll. under a gen. mapping
+#F PreImagesNC(,) set of preimages of a coll. under a gen. mapping
##
## <#GAPDoc Label="PreImages">
##
## PreImages
##
+##
##
+##
##
+##
##
##
## PreImages( map ) is the preimage of the general mapping
@@ -1152,18 +1185,24 @@ DeclareGlobalFunction( "PreImage" );
## entries do in general not correspond.)
##
##
-## delegates to when
-## called with one argument,
+## delegates to when called with one argument,
## and to resp. when
## called with two arguments.
##
-## If the second argument is not an element or a subset of the range of
-## the first argument, an error is signalled.
+## From &GAP; version 4.16.0 PreImages
+## has been renamed PreImagesNC throughout the library,
+## and PreImages now checks that elm or coll
+## belong to the range before calling PreImagesNC.
+##
+## When using PreImagesNC anything may happen if elm
+## or coll do not belong to the range of map.
+##
##
##
## <#/GAPDoc>
##
DeclareGlobalFunction( "PreImages" );
+DeclareGlobalFunction( "PreImagesNC" );
#############################################################################
diff --git a/lib/mapping.gi b/lib/mapping.gi
index 7ae902e971..5069534ba6 100644
--- a/lib/mapping.gi
+++ b/lib/mapping.gi
@@ -273,9 +273,9 @@ InstallGlobalFunction( PreImage, function ( arg )
fi;
if IsDomain( img ) or IsSSortedList( img ) then
- return PreImagesSet( map, img );
+ return PreImagesSetNC( map, img );
elif IsHomogeneousList( img ) then
- return PreImagesSet( map, Set( img ) );
+ return PreImagesSetNC( map, Set( img ) );
fi;
# preimage of the empty list
@@ -297,10 +297,68 @@ end );
#############################################################################
##
-#F PreImages( ) . . . set of preimages of the range of a gen. mapping
-#F PreImages(,) . set of preimages of an elm under a gen. mapping
-#F PreImages(,) set of preimages of a coll. under a gen. mapping
+#F PreImages()
+#F PreImagesNC() . . . set of preimages of the range of a gen. mapping
+#F PreImages(,)
+#F PreImagesNC(,) set of preimages of an elm under a gen. mapping
+#F PreImages(,)
+#F PreImagesNC(,) set of preimages of a coll. under a gen. mapping
##
+InstallGlobalFunction( PreImagesNC, function ( arg )
+
+ local map, # mapping , first argument
+ img; # element , second argument
+
+ # preimage of the range under
+ if Length( arg ) = 1 then
+
+ return PreImagesRange( arg[1] );
+
+ elif Length( arg ) = 2 then
+
+ map := arg[1];
+ img := arg[2];
+
+ if not IsGeneralMapping( map ) then
+ ErrorNoReturn( " must be a general mapping" );
+ fi;
+
+ # preimage of a single element under
+ if FamRangeEqFamElm( FamilyObj( map ), FamilyObj( img ) ) then
+ if not img in Range( map ) then
+ ErrorNoReturn( " must be an element of Range()" );
+ fi;
+ return PreImagesElmNC( map, img );
+
+ # preimage of a collection of elements under
+ elif CollFamRangeEqFamElms( FamilyObj( map ), FamilyObj( img ) ) then
+ if not IsSubset( Range( map ), img ) then
+ ErrorNoReturn( "the collection must be contained in ",
+ "Range()" );
+ fi;
+
+ if IsDomain( img ) or IsSSortedList( img ) then
+ return PreImagesSetNC( map, img );
+ elif IsHomogeneousList( img ) then
+ return PreImagesSetNC( map, Set( img ) );
+ fi;
+
+ # preimage of the empty list
+ elif IsList( img ) and IsEmpty( img ) then
+
+ return [];
+
+ else
+ ErrorNoReturn( "the families of the element or collection ",
+ "and Range() don't match, ",
+ "maybe is not contained in Range() or ",
+ "is not a homogeneous list or collection" );
+ fi;
+ fi;
+ ErrorNoReturn( "usage: PreImagesNC(), PreImagesNC(,), ",
+ "PreImagesNC(,)" );
+end );
+
InstallGlobalFunction( PreImages, function ( arg )
local map, # mapping , first argument
@@ -1067,16 +1125,17 @@ InstallMethod( PreImageElm,
"for inj. & surj. general mapping, and element",
FamRangeEqFamElm,
[ IsGeneralMapping and IsInjective and IsSurjective, IsObject ], 0,
- PreImagesRepresentative );
+ PreImagesRepresentativeNC );
#############################################################################
##
#M PreImagesElm( , ) . . . . . . for general mapping and element
+#M PreImagesElmNC( , ) . . . . . for general mapping and element
##
## more or less delegate to `ImagesElm'
##
-InstallMethod( PreImagesElm,
+InstallMethod( PreImagesElmNC,
"for general mapping with finite source, and element",
FamRangeEqFamElm,
[ IsGeneralMapping, IsObject ], 0,
@@ -1093,12 +1152,26 @@ InstallMethod( PreImagesElm,
fi;
end );
+InstallMethod( PreImagesElm,
+ "for general mapping with finite source, and element",
+ FamRangeEqFamElm,
+ [ IsGeneralMapping, IsObject ], 0,
+ function ( map, elm )
+
+ if not ( elm in Image( map ) ) then
+ return fail;
+ else
+ return PreImagesElmNC( map, elm );
+ fi;
+ end );
+
#############################################################################
##
-#M PreImagesElm( , ) for const. time access gen. map., and elm.
+#M PreImagesElm( , ) . for const. time access gen. map., and elm.
+#M PreImagesElmNC( , ) for const. time access gen. map., and elm.
##
-InstallMethod( PreImagesElm,
+InstallMethod( PreImagesElmNC,
"for constant time access general mapping, and element",
FamRangeEqFamElm,
[ IsGeneralMapping and IsConstantTimeAccessGeneralMapping, IsObject ], 0,
@@ -1113,12 +1186,25 @@ InstallMethod( PreImagesElm,
return preimgs;
end );
+InstallMethod( PreImagesElm,
+ "for constant time access general mapping, and element",
+ FamRangeEqFamElm,
+ [ IsGeneralMapping and IsConstantTimeAccessGeneralMapping, IsObject ], 0,
+ function( map, elm )
+ if not ( elm in Image( map ) ) then
+ return fail;
+ else
+ return PreImagesElmNC( map, elm );
+ fi;
+ end );
+
#############################################################################
##
#M PreImagesSet( , ) . for general mapping and finite collection
+#M PreImagesSetNC( , ) for general mapping and finite collection
##
-InstallMethod( PreImagesSet,
+InstallMethod( PreImagesSetNC,
"for general mapping, and finite collection",
CollFamRangeEqFamElms,
[ IsGeneralMapping, IsCollection ], 0,
@@ -1129,12 +1215,31 @@ InstallMethod( PreImagesSet,
fi;
primgs:= [];
for elm in Enumerator( elms ) do
- UniteSet( primgs, AsList( PreImagesElm( map, elm ) ) );
+ UniteSet( primgs, AsList( PreImagesElmNC( map, elm ) ) );
od;
return primgs;
end );
+
InstallMethod( PreImagesSet,
+ "for general mapping, and finite collection",
+ CollFamRangeEqFamElms,
+ [ IsGeneralMapping, IsCollection ], 0,
+ function( map, elms )
+ local im, elm;
+ if not IsFinite( elms ) then
+ TryNextMethod();
+ fi;
+ im:= Image( map );
+ for elm in Enumerator( elms ) do
+ if not (elm in im ) then
+ return fail;
+ fi;
+ od;
+ return PreImagesSetNC( map, elms );
+ end );
+
+InstallMethod( PreImagesSetNC,
"for general mapping, and empty list",
true,
[ IsGeneralMapping, IsList and IsEmpty ], 0,
@@ -1142,6 +1247,14 @@ InstallMethod( PreImagesSet,
return [];
end );
+InstallMethod( PreImagesSet,
+ "for general mapping, and empty list",
+ true,
+ [ IsGeneralMapping, IsList and IsEmpty ], 0,
+ function( map, elms )
+ return [];
+ end );
+
#############################################################################
##
@@ -1151,7 +1264,7 @@ InstallMethod( PreImagesRange,
"for general mapping",
true,
[ IsGeneralMapping ], 0,
- map -> PreImagesSet( map, Range( map ) ) );
+ map -> PreImagesSetNC( map, Range( map ) ) );
#############################################################################
@@ -1169,6 +1282,7 @@ InstallMethod( PreImagesRange,
#############################################################################
##
#M PreImagesRepresentative( , ) . . for s.p. gen. mapping & elm
+#M PreImagesRepresentativeNC( ,