229 Commits

Author SHA1 Message Date
John J. Camilleri
0c91c325be Simple hello world working with node-addon-api (C++) 2019-07-22 11:31:19 +02:00
John J. Camilleri
ba93141317 Clear old contents of src/runtime/javascript, add README for upcoming bindings 2019-07-15 11:30:21 +02:00
John J. Camilleri
12079550f8 Remove TypeScript runtime and point to new repository
https://github.com/GrammaticalFramework/gf-typescript
2019-07-11 09:29:49 +02:00
John J. Camilleri
1ceb8c0342 Merge pull request #45 from GrammaticalFramework/pgf2json
Add export to PGF JSON format
2019-07-10 19:32:49 +02:00
John J. Camilleri
eab9fb88aa Minor renamings in JSON format 2019-07-10 08:49:00 +02:00
John J. Camilleri
acd4a5e8cd Address @heatherleaf's suggestions 2019-07-10 08:45:23 +02:00
John J. Camilleri
a4b1fb03aa Whitespace fixes 2019-07-07 17:38:07 +02:00
John J. Camilleri
cb88b56016 Finish compile to PGF JSON, including JSON schema for resulting format. 2019-07-07 17:35:31 +02:00
John J. Camilleri
ecf9b41db0 Finish JSON conversion for abstract 2019-07-03 16:34:07 +02:00
John J. Camilleri
c5a75c482c Start work on PGFtoJSON module. Add compiler flag -f json. 2019-07-03 15:07:31 +02:00
krangelov
32379a8d11 fully supported case-insensitive parsing/lookup 2019-06-30 08:48:23 +02:00
krangelov
b56591c6b6 the parser now ensures that all word senses are in the chart 2019-06-25 12:58:28 +02:00
krangelov
b94bb50ec9 fix in gu_buf_heap_pop 2019-06-24 12:27:36 +02:00
krangelov
e2395335cb Merge branch 'master' of https://github.com/GrammaticalFramework/gf-core 2019-06-24 12:14:15 +02:00
krangelov
2d9478b973 share some code for printing 2019-06-24 12:13:14 +02:00
John J. Camilleri
17e3f753fb gflib.ts: put warning on console when function undefined 2019-06-13 14:43:21 +02:00
John J. Camilleri
498ad572ac gflib.ts: fix in annotation when type is unknown 2019-06-13 14:12:53 +02:00
John J. Camilleri
bc61f8c191 gflib.ts: generate source map, which is helpful for debugging 2019-06-13 13:53:58 +02:00
John J. Camilleri
d252cfd610 gflib.ts: handled unimplemented functions during linearisation 2019-06-13 10:31:49 +02:00
John J. Camilleri
46a1bdc7ea gflib.ts: also accept U+00C0-U+00FF (\192-\255) in idents in parseTree
Matches definition in src/compiler/GF/Grammar/Lexer.x
2019-06-12 15:28:25 +02:00
John J. Camilleri
18d0e1fad0 gflb.ts: add comments about startsWith polyfill, making into module 2019-06-12 09:51:27 +02:00
John J. Camilleri
ab94e93b94 Avoid modifying String prototype in TypeScript runtime
Adds new class TaggedString
2019-06-10 11:39:31 +02:00
John J. Camilleri
a229507392 Use strict mode in TypeScript, catch some more corner cases 2019-06-10 11:14:14 +02:00
John J. Camilleri
6a9c917b29 TypeScript readme 2019-06-10 10:19:43 +02:00
John J. Camilleri
9ba4a42426 Add generated gflib.js under typescript/js. Add deprecation notice in javascript. 2019-06-10 10:15:03 +02:00
John J. Camilleri
bbd1c9147a Catch for when rules are undefined 2019-06-10 09:48:44 +02:00
John J. Camilleri
4793d376d9 Create copies when tagging
Not sure if this behaviour is identical to previous version,
or in truth how important it really is anyway
2019-06-10 09:45:04 +02:00
John J. Camilleri
63606fd2d0 Minor indentation fixes in gflib.js
Despite it being deprecated 🙈
2019-06-10 09:29:43 +02:00
John J. Camilleri
d6a1e87f4a Support for pre in gflib.ts. Some type annotation fixes. 2019-06-07 21:17:41 +02:00
John J. Camilleri
ffcdaa921f Porting of JS runtime to TypeScript (gflib.ts) complete 2019-06-07 13:58:23 +02:00
John J. Camilleri
f2e03bfc51 Remove type definitions gflib.d.ts which contained many errors and now obsolete 2019-06-07 10:07:23 +02:00
John J. Camilleri
c89656f3ee More type fixes in gflib.ts after setting noImplicitAny 2019-06-07 10:06:19 +02:00
John J. Camilleri
c9b4318e9e Clean up whitespace in [old] gflib.js 2019-06-07 09:34:13 +02:00
John J. Camilleri
1e43e7be4b Fix all type errs in gflib.ts except tagging ones. Add TS/eslint configs.
gflib.js required changing the String prototype which I'm not sure I want to do here
2019-06-07 09:33:24 +02:00
John J. Camilleri
44261b7582 More progress on gflib.ts
All code has been copied from gflib.js but there are many type errors
yet to be resolved
2019-06-05 10:23:27 +02:00
John J. Camilleri
b980bce334 Add gflib.ts, a port of JS runtime gflib.js into TypeScript (WIP) 2019-06-04 15:16:17 +02:00
John J. Camilleri
bd7753db1a Update TypeScript definitions for gflib.js
Still not 100% tested: best solution will really be to rewrite
gflib.js in TypeScript and at the same time use ES modules
2019-05-29 14:43:28 +02:00
krangelov
8c18d7162f bits of documentation 2019-05-28 12:59:07 +02:00
krangelov
ac039ec74f filter out empty cohorts 2019-05-28 12:42:59 +02:00
krangelov
9f0ea19a1c API for scanning for cohorts in an arbitrary text 2019-05-28 12:26:00 +02:00
krangelov
8df2121650 Merge branch 'master' of https://github.com/GrammaticalFramework/gf-core 2019-05-27 09:06:11 +02:00
krangelov
8b9719bd2d remove duplicate definition for RecordCompare 2019-05-27 09:05:41 +02:00
Aarne Ranta
b7249adf63 reordered error message for 'no overload'; might be even better to show complete types 2019-05-20 15:58:47 +02:00
John J. Camilleri
7a3efdfeb9 Update link to RGL tutorial (now HTML version) 2019-05-20 10:36:35 +02:00
Thomas Hallgren
86066d4b12 Eliminate the dependency on time-compat
It was only needed for compatibility with directory<1.2, but
directory>=1.2 has been shipped with ghc since ghc-7.6.

Note: time-compat-1.9.* (the current version) is a completely different
package, that does not provide the needed function toUTCTime, which
was provided in time-compat-0.1.*.
2019-05-15 12:05:38 +02:00
John J. Camilleri
af62a99bf5 update_html rewrites anchors which Pandoc 1.16 doesn't process
See #43
2019-05-06 08:45:07 +02:00
John J. Camilleri
ac1f304722 Merge pull request #42 from gear0/master
corrected some minor typos in reference manual
2019-05-06 08:11:02 +02:00
gear0
92720b92a4 corrected some minor typos in reference manual 2019-05-05 12:09:31 +02:00
Inari Listenmaa
078440ffbf Merge pull request #41 from inariksit/js-doc
(doc) Update path to gflib.js
2019-05-03 18:54:06 +02:00
Inari Listenmaa
68919a5e42 (doc) Update path to gflib.js 2019-05-03 18:53:28 +02:00
Thomas Hallgren
a5a019a124 runtime/javascript: use a grammar.js with two langauges
grammar.js contained only one langauge: FoodsEng. Now it contains
FoodsEng and FoodsIta, similar to what's shown in the gf-tutorial.
The grammar comes from gf-contrib/tutorial/foods.
2019-05-03 15:19:19 +02:00
Thomas Hallgren
61fe167392 gf-tutorial: fix link to JavaScript translator demo
After fixing trivial problem in translator.html, the demo works, but
the example grammar contains only one langauge, so it is not so
interesting. translator.html is located in src/runtime/javascript.
The editor.html in the same location also works.
2019-05-03 14:52:28 +02:00
Aarne Ranta
fd29925173 started collecting error messages in order to explain them 2019-04-29 16:53:43 +02:00
Thomas Hallgren
bea6aa1d2d GF.Compile.CheckGrammar: discard bad 'lincat C = …' with a warning
e.g. if C is a fun and not a cat in the abstract syntax.
Discarding bad lincats prevents GF from generating malformed PGFs that
are rejected by the C run-time system.
I also added code to reject bad lincats with an error, but I left it
commented out since it seems a bit pedantic compared to GF's otherwise
rather sloppy grammar checking.
2019-04-25 17:02:42 +02:00
krangelov
c628e11c01 respect the probs option also when merging PGFs 2019-04-12 11:04:40 +02:00
Thomas Hallgren
61e7df4d1c Fix outdated comment about which version of the Haskell Platform to use 2019-04-05 16:38:12 +02:00
krangelov
de53a7c4db Merge branch 'master' of https://github.com/GrammaticalFramework/gf-core 2019-03-26 12:21:52 +01:00
krangelov
1e9188ea60 bugfix in the pretty printer 2019-03-26 12:21:35 +01:00
Thomas Hallgren
a55c7c7889 GF.Compile.GrammarToCanonical: keep unreachable rows in tables
since unreachable rows can become reachable after grammar transformation.
Also export smart constructors for projection and selection.
2019-03-22 15:38:02 +01:00
Aarne Ranta
b3387e80e4 hiding morphological tags from Latex printing of dependency trees 2019-03-20 22:19:32 +01:00
Thomas Hallgren
de0a997fcd Merge branch 'master' of https://github.com/GrammaticalFramework/gf-core 2019-03-20 14:40:17 +01:00
Thomas Hallgren
0f53431221 GF.Grammar.Canonical: pretty printer: omit some redundant brackets 2019-03-20 14:39:42 +01:00
krangelov
099f2de5b4 support cross-compilation from Linux to Windows 2019-03-19 12:43:38 +01:00
krangelov
2f2b39c5d2 Merge branch 'master' of https://github.com/GrammaticalFramework/gf-core 2019-03-19 11:22:09 +01:00
krangelov
f3d7d55752 added one more possible location for Java headers 2019-03-19 11:21:39 +01:00
Thomas Hallgren
2979864752 GF.Compile.GrammarToCanonical: allow + in reg exps in pre { } 2019-03-14 16:52:37 +01:00
Thomas Hallgren
b11d7d93dc GF.Grammar.Canonical: some Functor/Foldable/Traversable instances 2019-03-13 01:51:26 +01:00
Thomas Hallgren
ba9aeb3322 Merge branch 'master' of https://github.com/GrammaticalFramework/gf-core 2019-03-12 22:34:00 +01:00
Thomas Hallgren
8e2424af49 GF.Grammar.Canonical: add TuplePattern and CommentedValue 2019-03-12 22:32:54 +01:00
Peter Ljunglöf
01b9e8da8d canonical GF: flatten several concatenations into one json array, and parse the array back into concatenations 2019-03-08 18:33:56 +01:00
Peter Ljunglöf
926a5cf414 added parsing of json into canonical GF 2019-03-08 17:58:24 +01:00
Peter Ljunglöf
21140fc0c0 remove case expressions (no particular reason) 2019-03-08 17:57:02 +01:00
Peter Ljunglöf
3328279120 corrected json printing
some object labels must be preceded by ".", to not be in conflict with GF records (which are stored as json objects)
plus some minor bugfixes and cleaning
2019-03-08 17:35:35 +01:00
Peter Ljunglöf
8cf4446e8c Remove "canonical_yaml" from the option descriptions 2019-03-08 17:21:23 +01:00
Thomas Hallgren
5b401f3880 Expose GF.Grammar.Canonical + some refactoring
to make it available in other tools by depending on the gf package and
importing it
2019-03-07 17:41:16 +01:00
Thomas Hallgren
b783299b73 Rename module GF.Compile.ConcreteToCanonical to GF.Compile.GrammarToCanonical 2019-03-07 14:47:37 +01:00
Thomas Hallgren
0970d678cf haskell-bind/utils.c: add missing return
Found via C compiler warning
2019-03-07 14:11:29 +01:00
Thomas Hallgren
bf17fa0bb2 Bump version number to 3.10.3-git
This is not an announced realase, but this is version now installed on our
server.
2019-03-05 20:18:30 +01:00
Thomas Hallgren
0b3c278f49 Merge branch 'master' of https://github.com/GrammaticalFramework/gf-core 2019-03-05 19:23:54 +01:00
Thomas Hallgren
c710bf0e84 Update .deb packages to verion 3.10-2 on the download page
New .deb packages have been generated since it turned out that the
RGL was missing in original .deb packages.
2019-03-05 19:18:45 +01:00
Thomas Hallgren
eb46577f58 debian/rules bug fix: the RGL was not included in .deb packages
The problem was that the RGL was both built and copied to the destdir
during the build step, which caused it to be deleted before the install
step. It is now copied to destdir during the install step.
2019-03-05 16:19:46 +01:00
krangelov
52f2739da1 strip empty phrases in bracketedLinearize 2019-02-27 08:27:50 +01:00
krangelov
fc37bc26cd fixed typo on c-bracketedLinearize 2019-02-26 21:10:06 +01:00
krangelov
bde1a6d586 fix the dependency to json 2019-02-26 19:32:08 +01:00
krangelov
25dc934871 replace aeson with json 2019-02-26 19:27:36 +01:00
krangelov
2fdfef13d8 added command c-bracketedLinearize 2019-02-26 15:16:36 +01:00
Thomas Hallgren
a928e4657e Need aeson>=1.3
Also remove ununsed GF.Compile.PGFtoAbstract
2019-02-21 14:43:53 +01:00
Thomas H
b6fd9a7744 Merge pull request #34 from heatherleaf/master
Encode/decode of canonical grammars to/from JSON/YAML
2019-02-21 14:26:11 +01:00
krangelov
64a2483b12 added Data.Data.Data instance for Expr 2019-02-20 13:00:51 +01:00
krangelov
1d1e65185a fixes in the headers for use with Microsoft Visual C++ 2019-02-18 11:39:21 +01:00
krangelov
c32cd7133f fixes in the headers for compilation on Windows 2019-02-18 11:23:01 +01:00
krangelov
409731413e disable the parser debugger which was left enabled by accident 2019-02-14 15:33:21 +01:00
krangelov
8a5e7fa25d fix the reader for patterns in a def rule 2019-02-14 15:32:12 +01:00
krangelov
e05c79a751 different definition for GF_ARRAY_LEN 2019-02-14 15:31:36 +01:00
krangelov
ef21d08225 bugfix in computing record lengths 2019-02-14 15:29:33 +01:00
Peter Ljunglöf
f8346c4557 added helper info about canonical grammar output 2019-02-08 09:22:08 +01:00
Peter Ljunglöf
47ac01e4b9 enable export of canonical grammars to JSON and YAML 2019-02-08 09:10:48 +01:00
Peter Ljunglöf
a0c1da2548 encoding/decoding canonical GF grammars to/from JSON and YAML 2019-02-08 09:10:04 +01:00
Thomas Hallgren
951b884118 Export of concrete syntax to Haskell now goes via Canonical GF
TODO: better treatment of Predef functions and record subtyping coercions
2019-01-23 02:47:10 +01:00
Thomas Hallgren
fc5c2b5a22 PGF.Haskell.fromStr: fix double spaces caused by empty tokens 2019-01-23 02:45:23 +01:00
Thomas Hallgren
e4abff7725 More work on the canonica_gf export
+ Abstract syntax now is converted directly from the Grammar and not via PGF,
  so you can use `gf -batch -no-pmcfg -f canonical_gf ...`, to export to
  canonical_gf while skipping PMCFG and PGF file generation completely.
+ Flags that are normally copied to PGF files are now included in the
  caninical_gf output as well (in particular the startcat flag).
2019-01-22 17:16:32 +01:00
Thomas Hallgren
a40130ddc4 gfse: prevent scrolling during drag-and-drop on iOS
Applies to webkit-based browsers on other touch-based platforms too
2019-01-21 21:18:01 +01:00
Thomas Hallgren
71307d6518 Two fixes in GF.Grammar.Canonical
+ Hide Prelude.<> to avoid ambiguity with ghc-8.6
+ Vertical alternative in the pretty printer for table types A => B
2019-01-18 14:44:45 +01:00
Thomas Hallgren
fc1b51aa95 Adding -output-format canonical_gf
This output format converts a GF grammar to a "canonical" GF grammar. A
canonical GF grammar consists of

 - one self-contained module for the abstract syntax
 - one self-contained module per concrete syntax

The concrete syntax modules contain param, lincat and lin definitions,
everything else has been eliminated by the partial evaluator, including
references to resource library modules and functors. Record types
and tables are retained.

The -output-format canonical_gf option writes canonical GF grammars to a
subdirectory "canonical/". The canonical GF grammars are written as
normal GF ".gf" source files, which can be compiled with GF in the normal way.

The translation to canonical form goes via an AST for canonical GF grammars,
defined in GF.Grammar.Canonical. This is a simple, self-contained format that
doesn't cover everyting in GF (e.g. omitting dependent types and HOAS), but it
is complete enough to translate the Foods and Phrasebook grammars found in
gf-contrib. The AST is based on the GF grammar "GFCanonical" presented here:

  https://github.com/GrammaticalFramework/gf-core/issues/30#issuecomment-453556553

The translation of concrete syntax to canonical form is based on the
previously existing translation of concrete syntax to Haskell, implemented
in module GF.Compile.ConcreteToHaskell. This module could now be reimplemented
and simplified significantly by going via the canonical format. Perhaps exports
to other output formats could benefit by going via the canonical format too.

There is also the possibility of completing the GFCanonical grammar
mentioned above and using GF itself to convert canonical GF grammars to
other formats...
2019-01-17 21:04:08 +01:00
Thomas Hallgren
5fe963dd02 Fix compilation with ghc-7.10
NoMonadFailDesugaring is not supported by ghc-7.10, but it is only needed
with ghc>=8.6
2019-01-16 14:42:34 +01:00
John J. Camilleri
f32d222e71 Update links to Haskell docs on homepage 2019-01-10 08:58:34 +01:00
Prasanth Kolachina
a131b244df Merge pull request #25 from pkolachi/master
add CoNLLU as output format for gf2ud: merging issue (#24)
2019-01-07 13:26:44 +01:00
Prasanth Kolachina
0accd97691 add CoNLLU as output format for gf2ud: merging issue (#24) 2019-01-07 13:24:49 +01:00
Prasanth Kolachina
f8bd35543c Merge pull request #24 from odanoburu/gf2ud-comments
(gf2ud) add comments to CoNLL-U output
2019-01-07 13:18:45 +01:00
John J. Camilleri
a7b10ea936 Change refs from RGL's Make.* to Setup.* in dev guide 2018-12-22 13:59:32 +01:00
Krasimir Angelov
7c97e5566d fix after the change in bracketed string 2018-12-20 12:40:46 +01:00
Krasimir Angelov
7288425daf Merge branch 'master' of https://github.com/GrammaticalFramework/gf-core 2018-12-20 10:55:56 +01:00
Krasimir Angelov
260c0d07e0 revert to printing the unique id in ppBracketedString 2018-12-20 10:54:04 +01:00
Krasimir Angelov
26dabeab9b save the original concrete category in BracketedString 2018-12-20 10:52:45 +01:00
odanoburu
f7c2fb8a7d (gf2ud) add comments to CoNLL-U output
when debbuging labels, I find it useful to have comments saying what's
the original sentence (lazy, I know) and the original tree (depending
on the treebank, the trees can be similar).

I know this is not the goal exactly, but UDv2 treebanks
(http://universaldependencies.org/format.html) should always have a
'text =' comment, and a 'sent_id =' comment (which would be easy to
implement too, but not that useful).
2018-12-19 12:13:31 -02:00
John J. Camilleri
4bda53acb7 Update PGF API link to point to 3.9, as 3.10 has no docs on Hackage 2018-12-18 22:14:32 +01:00
Aarne Ranta
54204d2d95 added the possibility to annotate features of syncat words, e.g. @"is" PresSg3 2018-12-18 18:44:02 +01:00
Aarne Ranta
9834b89a30 refactored cnc configfile parsing a bit 2018-12-18 18:30:40 +01:00
Aarne Ranta
b3a2b53df2 Merge pull request #22 from pkolachi/master
fix conll output in gf2ud and allow comments in dependency configs
2018-12-18 19:06:25 +02:00
Aarne Ranta
77c0a8e100 Merge branch 'master' into master 2018-12-18 19:05:42 +02:00
Prasanth Kolachina
86233e9c28 morph. feat generation by AR 2018-12-18 16:53:35 +01:00
Aarne Ranta
40e7544a2b added morphological tags to UD tree output. Tags are give in CncConfiguration, e.g. @N Sg Pl. Default tag is Cat-offset, as defined for each Cat in pgf 2018-12-18 15:59:48 +01:00
Prasanth Kolachina
61c1510620 allow comments in dependency configs and fix conll output 2018-12-17 12:02:13 +01:00
krangelov
eb22112178 a pool where the smallest chunks are memory pages 2018-12-16 07:46:14 +01:00
John J. Camilleri
083aa96e57 TOC for Markdown should now work for both Pandoc < 2.0 and >= 2.0
The use of $toc$ and $table-of-contents$ flags changed, see:
https://pandoc.org/releases.html#pandoc-2.0-29-oct-2017
under "Behaviour changes"
2018-12-10 14:25:44 +01:00
John J. Camilleri
d82a53ebc6 Replace gf-refman.html with Markdown version gf-refman.md
The raw HTML was invalid, and this way we use the common website template
for a uniform look without any duplication.

It seems gf-refman.html was once generated from txt2tags, although I have
been unable to find this original .t2t file.
I also tried to re-generate txt2tags from HTML but was not able to.
However I was able to convert HTML to Markdown using Pandoc and I think
the result is pretty good, so I think we should use this.

The original gf-refman.html can be obtained from git history, e.g.:
a7e43d872f/doc/gf-refman.html
2018-12-09 20:38:02 +01:00
John J. Camilleri
5006b520d1 Area under footer is all gray even on short pages 2018-12-08 14:29:43 +01:00
John J. Camilleri
f78dfe80a2 Update doc/index page 2018-12-08 14:29:02 +01:00
John J. Camilleri
44ac326da0 Regnerate HTML if template changes 2018-12-08 13:57:04 +01:00
John J. Camilleri
a8b23d52a8 Fix some invalid HTML. 2018-12-08 13:47:27 +01:00
John J. Camilleri
d880a61857 Add some documentation to update_html 2018-12-06 13:47:50 +01:00
John J. Camilleri
7bd086ba19 Case-insensitve sed replacements handled the dumb way
Because BSD sed != GNU sed
2018-12-06 10:18:31 +01:00
John J. Camilleri
ff0fe0a6c5 Add reference to DG in homepage footer. Spacing in top links. 2018-12-06 09:30:49 +01:00
John J. Camilleri
ef4df27d1b Add link to open #gf in web chat 2018-12-06 09:13:52 +01:00
John J. Camilleri
e9e2bd6b89 Fix linking to chapters in gf-tutorial; Remove reference to Htmls. 2018-12-06 09:00:44 +01:00
John J. Camilleri
72a9eb0c8a Another fake change to trigger rebuild of gf-tutorial 2018-12-05 18:14:17 +01:00
John J. Camilleri
b73f033b08 Rewrite <a name=...> to <div id=...> to preserve page anchors in Pandoc 2018-12-05 16:11:33 +01:00
John J. Camilleri
b974c09951 Update runtime-api.html to match the new visual look of the GF website 2018-12-05 15:48:07 +01:00
John J. Camilleri
159b6ee331 Fake change to trigger rebuild of gf-tutorial 2018-12-05 11:41:41 +01:00
John J. Camilleri
3dec78c21c Clarifications on download page: binary packages include RGL 2018-12-05 08:30:25 +01:00
John J. Camilleri
6ad9bf3dbf Add Stack files for different GHC versions 2018-12-04 10:32:26 +01:00
John J. Camilleri
ee5ac81dfc Make GF compile with GHC 8.6.2
- Re-implement `Distribution.Simple.BuildPaths.exeExtension`
- Turn off `MonadFailDesugaring`

Tested with GHC:

- 7.10.3
- 8.0.2
- 8.2.2
- 8.4.3
- 8.6.2

Yay Stack!
2018-12-04 10:31:53 +01:00
Thomas Hallgren
1a842efeaf downloads: add .deb package for Ubuntu (32-bit) 2018-12-03 16:10:01 +01:00
Thomas Hallgren
de005b9df3 Merge branch 'master' of https://github.com/GrammaticalFramework/gf-core 2018-12-03 15:53:36 +01:00
Thomas Hallgren
52bc0f566e debian/control: new dependency: pandoc
This should have been added before the 3.10 release
2018-12-03 15:52:52 +01:00
John J. Camilleri
b509d08cbf Add Travis build images to release notes 2018-12-03 15:47:45 +01:00
John J. Camilleri
fd0ee2756a Indent nested lists in Markdown by 4 spaces instead of 2 2018-12-03 15:44:44 +01:00
John J. Camilleri
34e89ac710 Put GF logo on the right again 2018-12-03 15:27:55 +01:00
John J. Camilleri
331d73b566 Update release notes RGL section (not much) 2018-12-03 15:25:05 +01:00
John J. Camilleri
8d460ac402 Update 3.10 release notes after going through all gf-core commits since 2017-08-11 2018-12-03 15:04:21 +01:00
John J. Camilleri
5546c6d6da Update clean_html to handle markdown sources too 2018-12-03 10:49:37 +01:00
John J. Camilleri
c380288db8 Put floating logo on left 2018-12-03 10:49:15 +01:00
Thomas Hallgren
bd7bb9b34a Merge branch 'master' of https://github.com/GrammaticalFramework/gf-core 2018-12-03 01:34:49 +01:00
Thomas Hallgren
18251e57a3 debian/changelog: updated release date 2018-12-03 01:33:52 +01:00
Thomas Hallgren
d06539c35c Merge branch 'master' of https://github.com/GrammaticalFramework/gf-core 2018-12-02 21:21:18 +01:00
Thomas Hallgren
60738dda6d gf.cabal: update tested-with 2018-12-02 21:20:54 +01:00
John J. Camilleri
e628e3fe0f Add news item for 3.10 release 2018-12-02 21:18:38 +01:00
Thomas Hallgren
769743c5c0 Minor fixes on the GF 3.10 download page 2018-12-02 15:29:55 +01:00
Thomas Hallgren
1c75d417ee Move 3.10 download page into place, update release date 2018-12-02 15:08:40 +01:00
John J. Camilleri
5c518de0f2 Updates to download page for 3.10 2018-12-01 19:52:33 +01:00
Thomas Hallgren
e6c2c844e9 GF.Main: leave the code page unchanged on Windows
This should make it easier to use GF with UTF-8 in the Windows Console
See https://groups.google.com/forum/#!topic/gf-dev/DCou6FDhCnU
2018-12-01 15:53:58 +01:00
Thomas Hallgren
883a7a95a1 build-binary-dist.sh: make it easy to choose which version of ghc to use 2018-12-01 15:53:27 +01:00
Aarne Ranta
831252eb81 dealing with ',' as syncategorematic token 2018-12-01 09:32:22 +01:00
Krasimir Angelov
fdc5659f80 Merge pull request #19 from MUSTE-Project/master
Fix deprecations from containers >= 0.4.0.0
2018-11-30 12:18:24 +01:00
Peter Ljunglöf
4d34c7f66b Fix deprecations from containers >= 0.4.0.0
E.g. `foldWithKey` has been deprecated since 0.4.0.0 (November 2010)[1] and has been removed in 0.6.0.1 (2018)[2]

[1]: https://github.com/haskell/containers/blob/master/changelog.md#0400--nov-2010
[2]: https://github.com/haskell/containers/blob/master/changelog.md#death-of-deprecated-functions

(commit originally by @fredefox)
2018-11-30 11:52:56 +01:00
Krasimir Angelov
f898c250ba removed instructions which doesn't actually work 2018-11-30 11:05:59 +01:00
Thomas Hallgren
5ef390f188 Merge branch 'master' of https://github.com/GrammaticalFramework/gf-core 2018-11-30 00:47:10 +01:00
Thomas Hallgren
fa5c6a2949 Fix spelling mistake on GF 3.9 download page 2018-11-30 00:46:24 +01:00
Thomas Hallgren
d0bc368358 Update make deb for the GF 3.10 release
This includes adding commands in debian/rules to build and include
the RGL and the example grammars in the debian package.
2018-11-30 00:17:45 +01:00
Thomas Hallgren
e0dca729d6 WebSetup.hs: don't output messages that lie about what's being installed 2018-11-30 00:15:37 +01:00
Thomas Hallgren
47c983c625 gf.cabal: remove redundant dependency on old-locale 2018-11-29 23:06:30 +01:00
John J. Camilleri
01f61c526f Custom CSS comes after libraries; add include-before/after (not actively used) 2018-11-29 13:06:52 +01:00
John J. Camilleri
538fe5bddb Don't wrap dates on hompage 2018-11-29 13:00:26 +01:00
John J. Camilleri
f4052c8a5e Add basic favicon.ico 2018-11-29 10:46:33 +01:00
John J. Camilleri
e0a3b0030e Remove some t2t frontmatter from shell-reference, to trigger update 2018-11-29 10:45:54 +01:00
John J. Camilleri
b30456aa0c Rename _template.html to template.html 2018-11-29 10:35:43 +01:00
John J. Camilleri
61c58316ea Remove overflow-x:scroll from title 2018-11-29 10:16:32 +01:00
John J. Camilleri
001d036a2c Remove t2t frontmatter from gf-editor-modes
Trying to force a rebuild
2018-11-29 09:55:28 +01:00
John J. Camilleri
fe7d01f7e3 Minors in footer 2018-11-28 22:34:04 +01:00
John J. Camilleri
a7e43d872f Merge branch 'new-website' 2018-11-28 22:22:41 +01:00
John J. Camilleri
d6fc50b40b Hide release announcement from homepage news 2018-11-28 22:21:56 +01:00
John J. Camilleri
9e02319b6d Better responsiveness, homepage and footer 2018-11-28 22:14:58 +01:00
John J. Camilleri
6278deb7a2 Page uses available width better, no jumping margins 2018-11-28 21:51:16 +01:00
Aarne Ranta
c6ec8cf302 fixed a bug in the cnclabel format 2018-11-28 19:56:47 +01:00
John J. Camilleri
07768ba4c4 Revert "Completely remove uses of example-based"
This reverts commit 69cea20dac.
2018-11-28 19:23:05 +01:00
John J. Camilleri
e2401f32ca Revert "remove the example-based folder. The code is still in the archive"
This reverts commit 05c2cfb628.
2018-11-28 19:22:19 +01:00
John J. Camilleri
69cea20dac Completely remove uses of example-based 2018-11-28 18:09:56 +01:00
Thomas Hallgren
32ce03dc94 bin/build-binary-dist.sh: include the RGL in binary distributions
TODO: the corresponding changes in debian/rules
2018-11-28 17:27:29 +01:00
John J. Camilleri
83abaa9b44 Put 3.9 page instead of 3.10 until release is final 2018-11-28 15:52:20 +01:00
John J. Camilleri
c7a14537c1 Update top links and footer during hackathon 2018-11-28 15:42:11 +01:00
Krasimir Angelov
8560b4fb65 Merge branch 'master' of https://github.com/GrammaticalFramework/gf-core 2018-11-28 15:33:24 +01:00
Krasimir Angelov
b0c3aef6ec add a few missing special tokens to the reference 2018-11-28 15:32:43 +01:00
John J. Camilleri
6352799ccb Merge branch 'master' into new-website
# Conflicts:
#	index.html
2018-11-28 14:47:20 +01:00
John J. Camilleri
a45c735545 Update LICENSE 2018-11-28 14:40:36 +01:00
Krasimir Angelov
05c2cfb628 remove the example-based folder. The code is still in the archive 2018-11-28 14:34:15 +01:00
Krasimir Angelov
69ad1e617e Merge branch 'master' of https://github.com/GrammaticalFramework/gf-core 2018-11-28 14:25:53 +01:00
Krasimir Angelov
eb2774af2b remove two obsolete options 2018-11-28 14:25:29 +01:00
John J. Camilleri
9b28d21b0a Remove Htmls.hs 2018-11-28 13:48:40 +01:00
John J. Camilleri
507236fdcd remove gf-server.cabal 2018-11-28 13:40:16 +01:00
John J. Camilleri
397f18a298 remove custom-binary flag; update Cabal version restriction; bump version to 3.10 2018-11-28 13:36:11 +01:00
John J. Camilleri
b1611eccd8 Make refman look up-to-date ish 2018-11-27 23:27:16 +01:00
John J. Camilleri
c8eb1010c5 Remove faq. Update people page. Add SS to news. 2018-11-27 23:12:21 +01:00
John J. Camilleri
14d35c8a31 Various fixes & cleanup in doc/ folder 2018-11-27 22:51:44 +01:00
John J. Camilleri
9bf5c98509 Work on new download page. Change 18-12 to 4.0.0 2018-11-27 22:36:57 +01:00
John J. Camilleri
8821f8baa8 Check all historic download and release pages 2018-11-27 22:14:01 +01:00
John J. Camilleri
8a45d23d63 Minors to homepage 2018-11-27 21:58:19 +01:00
Krasimir Angelov
abf3911b70 expose PGF and Concr for FFI 2018-11-27 21:09:35 +01:00
John J. Camilleri
735f5ff76f Remove src/ui folder, moved to:
https://github.com/GrammaticalFramework/gf-offline-translator
2018-11-15 10:33:31 +01:00
John J. Camilleri
cb0e919bf5 Link to new synopsis page 2018-11-13 21:22:54 +01:00
John J. Camilleri
d1a435ad9d Remove unnecessary CSS from template 2018-11-09 09:08:59 +01:00
John J. Camilleri
69ba677136 Add 3 top buttons, responsive columns 2018-11-09 08:40:06 +01:00
John J. Camilleri
406eec6690 GF logo links to home; remove "other demos" 2018-11-08 22:52:08 +01:00
John J. Camilleri
2f1ee094d2 Add download/index.md as demo of working Markdown rendering to HTML
Archive 3.9 pages and mark current ones for 18-12
2018-11-08 22:46:30 +01:00
John J. Camilleri
422248f11f Move unused pgf-binary into its own repository, at:
https://github.com/GrammaticalFramework/pgf-binary
2018-11-07 10:07:20 +01:00
John J. Camilleri
d46682bc29 Clean up stack file
Removed alex/happy as build-deps, if needed they can be installed with
`stack install alex happy`
2018-11-07 09:57:45 +01:00
Thomas Hallgren
8596fc5d26 Revert CSS change that produces overlapping text instead of responsive layout 2018-11-06 23:49:06 +01:00
John J. Camilleri
4958aab518 Add happy and alex as deps in Stack file 2018-11-05 09:59:06 +01:00
John J. Camilleri
390a6a04a1 New update_html runx txt2tags followed by pandoc
TODO: handle txt2tags macros in date, e.g.
`%%mtime(%F)` in download/encoding-change.t2t
2018-11-04 21:17:20 +01:00
John J. Camilleri
37e0754cf0 Fix encoding on tutorial 2018-11-04 21:12:32 +01:00
John J. Camilleri
a7b2f77227 Cleanup links in homepage and footer 2018-11-04 21:12:10 +01:00
John J. Camilleri
9a7862ea9e Links in footer 2018-11-04 19:58:18 +01:00
John J. Camilleri
914d54255f Comments in update_html script 2018-11-04 19:29:56 +01:00
John J. Camilleri
aea8548930 update_html also takes individual arguments 2018-11-04 19:27:14 +01:00
John J. Camilleri
99dad48961 Use Pandoc instead of txt2tags binary, much more configurable 2018-11-04 15:11:35 +01:00
John J. Camilleri
0b4d9cbea1 Add note about using Stack in download/index 2018-11-03 14:34:26 +01:00
John J. Camilleri
1010b9e49a Add stack file, using image for GHC 8.2.2 2018-11-03 14:28:31 +01:00
John J. Camilleri
f7dc9a6eaf Merge branch 'master' into new-website 2018-11-02 14:07:00 +01:00
John J. Camilleri
7867c8c828 pre and post HTML templates for all txt2tags conversions
Remaining: cleaning of t2t files (remove unnecessary options)
2018-10-31 15:47:12 +01:00
John J. Camilleri
632cd1e522 Refresh home page using basic Bootstrap 2018-10-31 14:13:05 +01:00
488 changed files with 8843 additions and 39899 deletions

20
.gitignore vendored
View File

@@ -39,8 +39,24 @@ src/runtime/c/sg/.dirstamp
src/runtime/c/stamp-h1
src/runtime/java/.libs/
src/runtime/python/build/
src/ui/android/libs/
src/ui/android/obj/
.cabal-sandbox
cabal.sandbox.config
.stack-work
DATA_DIR
# Generated documentation (not exhaustive)
demos/index-numbers.html
demos/resourcegrammars.html
demos/translation.html
doc/tutorial/gf-tutorial.html
doc/index.html
doc/gf-bibliography.html
doc/gf-developers.html
doc/gf-editor-modes.html
doc/gf-people.html
doc/gf-refman.html
doc/gf-shell-reference.html
doc/icfp-2012.html
download/*.html
gf-book/index.html
src/www/gf-web-api.html

19
LICENSE
View File

@@ -8,24 +8,9 @@ other. For this reason the different components have different licenses.
In summary:
- the GF compiler in the folder src/compiler and the PGF Web service in src/server
are under the GNU GENERAL PUBLIC LICENSE.
are under the GNU GENERAL PUBLIC LICENSE.
- the GF runtime in src/runtime is under dual GNU LESSER GENERAL PUBLIC LICENSE
and BSD LICENSE
- the resource grammar library in lib/src is under GNU LESSER GENERAL PUBLIC LICENSE.
However the user have the right to choose any license for any application grammar
derived from the resource grammar by using the grammar API.
- the resource grammar library also includes large coverage lexicons for some languages.
Since these lexicons are derived from external sources they might be under different licenses.
Look at the source file for every lexicon for details. The lexicons that we currently have
are:
lib/src/bulgarian/ DictBul.gf DictBulAbs.gf for Bulgarian
lib/src/english/ DictEng.gf DictEngAbs.gf for English
lib/src/turkish/ DictTur.gf DictTurAbs.gf for Turkish
lib/src/swedish/ DictSwe.gf DictSweAbs.gf for Swedish
- the GF runtime in src/runtime is under dual GNU LESSER GENERAL PUBLIC LICENSE and BSD LICENSE
The rest of this document contains copies of the GPL, LGPL and BSD licenses
which are applicable to the different components of Grammatical Framework

View File

@@ -20,6 +20,7 @@ doc:
clean:
cabal clean
bash bin/clean_html
gf:
cabal build rgl-none
@@ -32,7 +33,7 @@ html::
# number to the top of debian/changelog.
# (Tested on Ubuntu 15.04. You need to install dpkg-dev & debhelper.)
deb:
dpkg-buildpackage -b
dpkg-buildpackage -b -uc
# Make an OS X Installer package
pkg:

View File

@@ -37,13 +37,6 @@ The simplest way of installing GF is with the command:
cabal install
```
This can be broken down into the usual sub-steps:
```
cabal configure
cabal build
cabal copy
```
For more details, see the [download page](http://www.grammaticalframework.org/download/index.html)
and [developers manual](http://www.grammaticalframework.org/doc/gf-developers.html).

View File

@@ -1,3 +1,4 @@
import Distribution.System(Platform(..),OS(..))
import Distribution.Simple(defaultMainWithHooks,UserHooks(..),simpleUserHooks)
import Distribution.Simple.LocalBuildInfo(LocalBuildInfo(..),absoluteInstallDirs,datadir)
import Distribution.Simple.Setup(BuildFlags(..),Flag(..),InstallFlags(..),CopyDest(..),CopyFlags(..),SDistFlags(..))
@@ -73,5 +74,9 @@ dataDirFile = "DATA_DIR"
default_gf :: LocalBuildInfo -> FilePath
default_gf lbi = buildDir lbi </> exeName' </> exeNameReal
where
-- shadows Distribution.Simple.BuildPaths.exeExtension, which changed type signature in Cabal 2.4
exeExtension = case hostPlatform lbi of
Platform arch Windows -> "exe"
_ -> ""
exeName' = "gf"
exeNameReal = exeName' <.> exeExtension

View File

@@ -70,7 +70,7 @@ buildWeb gf flags (pkg,lbi) = do
gf_lib_path = datadir (absoluteInstallDirs pkg lbi dest) </> "lib"
args = numJobs flags++["-make","-s"] -- ,"-optimize-pgf"
++["--gfo-dir="++tmp_dir,
"--gf-lib-path="++gf_lib_path,
--"--gf-lib-path="++gf_lib_path,
"--name="++dropExtension pgf,
"--output-dir="++gfo_dir]
++[dir</>file|file<-src]
@@ -104,9 +104,10 @@ setupWeb dest (pkg,lbi) = do
copy_pgf (pgf,subdir,_) =
do let src = gfo_dir </> pgf
let dst = grammars_dir </> pgf
putStrLn $ "Installing "++dst
ex <- doesFileExist src
if ex then copyFile src dst else return ()
if ex then do putStrLn $ "Installing "++dst
copyFile src dst
else putStrLn $ "Not installing "++dst
gf_logo = "gf0.png"

View File

@@ -2,7 +2,7 @@
### This script builds a binary distribution of GF from the source
### package that this script is a part of. It assumes that you have installed
### the Haskell Platform, version 2013.2.0.0 or 2012.4.0.0.
### a recent version of the Haskell Platform.
### Two binary package formats are supported: plain tar files (.tar.gz) and
### OS X Installer packages (.pkg).
@@ -16,13 +16,14 @@ name="gf-$ver"
destdir="$PWD/dist/$name" # assemble binary dist here
prefix=${PREFIX:-/usr/local} # where to install
fmt=${FMT:-tar.gz} # binary package format (tar.gz or pkg)
ghc=${GHC:-ghc} # which Haskell compiler to use
extralib="$destdir$prefix/lib"
extrainclude="$destdir$prefix/include"
extra="--extra-lib-dirs=$extralib --extra-include-dirs=$extrainclude"
set -e # Stop if an error occurs
set -x # print commands before exuting them
set -x # print commands before executing them
## First configure & build the C run-time system
pushd src/runtime/c
@@ -64,13 +65,30 @@ else
fi
## Build GF, with C run-time support enabled
cabal install --only-dependencies -fserver -fc-runtime $extra
cabal configure --prefix="$prefix" -fserver -fc-runtime $extra
cabal install -w "$ghc" --only-dependencies -fserver -fc-runtime $extra
cabal configure -w "$ghc" --prefix="$prefix" -fserver -fc-runtime $extra
DYLD_LIBRARY_PATH="$extralib" LD_LIBRARY_PATH="$extralib" cabal build
# Building the example grammars will fail, because the RGL is missing
cabal copy --destdir="$destdir" # create www directory
## Build the RGL and copy it to $destdir
PATH=$PWD/dist/build/gf:$PATH
export GF_LIB_PATH="$(dirname $(find "$destdir" -name www))/lib" # hmm
mkdir -p "$GF_LIB_PATH"
pushd ../gf-rgl
make build
make copy
popd
# Build GF again, including example grammars that need the RGL
DYLD_LIBRARY_PATH="$extralib" LD_LIBRARY_PATH="$extralib" cabal build
## Copy GF to $destdir
cabal copy --destdir="$destdir"
libdir=$(dirname $(find "$destdir" -name PGF.hi))
cabal register --gen-pkg-config=$libdir/gf-$ver.conf
## Create the binary distribution package
case $fmt in
tar.gz)
targz="$name-bin-$hw-$os.tar.gz" # the final tar file

20
bin/clean_html Executable file
View File

@@ -0,0 +1,20 @@
#!/bin/bash
# This script finds all .t2t (txt2tags) and .md (Markdown) files
# and deletes the corresponding HTML file of the same name.
find . -name '*.t2t' | while read t2t ; do
html="${t2t%.t2t}.html"
if [ -f "$html" ] ; then
echo "$html"
rm -f "$html"
fi
done
find . -name '*.md' | while read md ; do
html="${md%.md}.html"
if [ -f "$html" ] ; then
echo "$html"
rm -f "$html"
fi
done

146
bin/template.html Normal file
View File

@@ -0,0 +1,146 @@
<!DOCTYPE html>
<html xmlns="http://www.w3.org/1999/xhtml" lang="$lang$" xml:lang="$lang$"$if(dir)$ dir="$dir$"$endif$>
<head>
<meta charset="utf-8" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
$for(author-meta)$
<meta name="author" content="$author-meta$" />
$endfor$
$if(date-meta)$
<meta name="dcterms.date" content="$date-meta$" />
$endif$
$if(keywords)$
<meta name="keywords" content="$for(keywords)$$keywords$$sep$, $endfor$" />
$endif$
<title>$if(title-prefix)$$title-prefix$ $endif$$pagetitle$</title>
<link rel="stylesheet" href="https://stackpath.bootstrapcdn.com/bootstrap/4.1.3/css/bootstrap.min.css" integrity="sha384-MCw98/SFnGE8fJT3GXwEOngsV7Zt27NXFoaoApmYm81iuXoPkFOJwJ8ERdknLPMO" crossorigin="anonymous">
<link rel="stylesheet" href="https://use.fontawesome.com/releases/v5.4.2/css/all.css" integrity="sha384-/rXc/GQVaYpyDdyxK+ecHPVYJSN9bmVFBvjA/9eOB+pb3F2w2N6fc5qB9Ew5yIns" crossorigin="anonymous">
$for(css)$
<link rel="stylesheet" href="$css$" />
$endfor$
$if(math)$
$math$
$endif$
<!--[if lt IE 9]>
<script src="//cdnjs.cloudflare.com/ajax/libs/html5shiv/3.7.3/html5shiv-printshiv.min.js"></script>
<![endif]-->
$for(header-includes)$
$header-includes$
$endfor$
</head>
<body class="bg-light">
<div class="bg-white pb-5">
$for(include-before)$
$include-before$
$endfor$
<div class="container-fluid py-5" style="max-width:1200px">
$if(title)$
<header id="title-block-header">
<a href="$rel-root$" title="Home">
<img src="$rel-root$/doc/Logos/gf1.svg" height="200" class="float-md-right ml-3 mb-3 bg-white" alt="GF Logo">
</a>
<h1 class="title">$title$</h1>
$if(subtitle)$
<p class="subtitle">$subtitle$</p>
$endif$
$for(author)$
<p class="author">$author$</p>
$endfor$
$if(date)$
<p class="date">$date$</p>
$endif$
</header>
$endif$
$if(toc)$
<nav id="$idprefix$TOC">
$if(table-of-contents)$
<!-- pandoc >= 2.0 -->
$table-of-contents$
$else$
<!-- pandoc < 2.0 -->
$toc$
$endif$
</nav>
$endif$
$body$
</div><!-- .container -->
</div><!-- .bg-white -->
<footer class="py-5">
<div class="container">
<div class="row">
<div class="col-6 col-sm-3">
<a href="$rel-root$">
<i class="fas fa-home"></i>
Home
</a>
<h6 class="text-muted mt-3">Get started</h6>
<ul class="list-unstyled">
<li><a href="https://www.youtube.com/watch?v=x1LFbDQhbso">Google Tech Talk</a></li>
<li><a href="http://cloud.grammaticalframework.org/">GF Cloud</a></li>
<li>
<a href="$rel-root$/doc/tutorial/gf-tutorial.html">Tutorial</a>
/
<a href="$rel-root$/lib/doc/rgl-tutorial/index.html">RGL Tutorial</a>
</li>
<li><a href="$rel-root$/download"><strong>Download GF</strong></a></li>
</ul>
</div>
<div class="col-6 col-sm-3">
<h6 class="text-muted">Learn more</h6>
<ul class="list-unstyled">
<li><a href="$rel-root$/gf-book">The GF Book</a></li>
<li><a href="$rel-root$/doc/gf-refman.html">Reference Manual</a></li>
<li><a href="$rel-root$/doc/gf-shell-reference.html">GF Shell Reference</a></li>
<li><a href="http://www.molto-project.eu/sites/default/files/MOLTO_D2.3.pdf">Best Practices</a></li>
<li><a href="$rel-root$/lib/doc/synopsis/index.html"><strong>RGL Synopsis</strong></a></li>
</ul>
</div>
<div class="col-6 col-sm-3">
<h6 class="text-muted">Develop</h6>
<ul class="list-unstyled">
<li><a href="$rel-root$/doc/gf-developers.html">Developers Guide</a></li>
<li><a href="http://hackage.haskell.org/package/gf/docs/PGF.html">PGF library API (Haskell runtime)</a></li>
<li><a href="$rel-root$/doc/runtime-api.html">PGF library API (C runtime)</a></li>
<li><a href="http://hackage.haskell.org/package/gf/docs/GF.html">GF compiler API</a></li>
<li><a href="$rel-root$/doc/gf-editor-modes.html">Text Editor Support</a></li>
</ul>
</div>
<div class="col-6 col-sm-3">
<h6 class="text-muted">Contribute</h6>
<ul class="list-unstyled">
<li><a href="http://groups.google.com/group/gf-dev">Mailing List</a></li>
<li><a href="https://github.com/GrammaticalFramework/gf-core/issues">Issue Tracker</a></li>
<li><a href="$rel-root$/doc/gf-people.html">Authors</a></li>
<li><a href="http://school.grammaticalframework.org/2018/">Summer School</a></li>
</ul>
<h6 class="text-muted">
Repositories
<i class="fab fa-github ml-1"></i>
</h6>
<a href="https://github.com/GrammaticalFramework/gf-core">GF</a> ·
<a href="https://github.com/GrammaticalFramework/gf-rgl">RGL</a> ·
<a href="https://github.com/GrammaticalFramework/gf-contrib">Contributions</a>
</div>
</div>
</div>
</footer>
$for(include-after)$
$include-after$
$endfor$
<script type="text/javascript">
var gaJsHost = (("https:" == document.location.protocol) ? "https://ssl." : "http://www.");
document.write(unescape("%3Cscript src='" + gaJsHost + "google-analytics.com/ga.js' type='text/javascript'%3E%3C/script%3E"));
</script>
<script type="text/javascript">
try {
var pageTracker = _gat._getTracker("UA-7811807-3");
pageTracker._trackPageview();
} catch(err) {}</script>
</body>
</html>

View File

@@ -1,11 +1,156 @@
#!/bin/bash
### This script finds all .t2t (txt2tags) files and updates the corresponding
### .html file, if it is out-of-date.
# Generate HTML from txt2tags (.t2t) and Markdown (.md)
# Usage:
# - update_html
# Look for all .t2t and .md files in the current directory and below,
# generating the output HTML when the source is newer than the HTML.
# - update_html path/to/file.t2t path/to/another.md
# Generate HTML for the specified file(s), ignoring modification time.
#
# Requires:
# - txt2tags for .t2t files. Tested with 2.6.
# - pandoc for both .t2t and .md files. Tested with 1.16.0.2 and 2.3.1.
# - the template file `template.html` in the same directory as this script.
#
# Tested with Ubuntu 16.04 and macOS Mojave.
#
# See also clean_html for removing the files generated by this script.
find . -name '*.t2t' | while read t2t ; do
html="${t2t%.t2t}.html"
if [ "$t2t" -nt "$html" ] ; then
txt2tags -thtml "$t2t"
# Path to directory where this script is
# https://stackoverflow.com/a/246128/98600
DIR="$( cd "$( dirname "${BASH_SOURCE[0]}" )" >/dev/null && pwd )"
# HTML template
template="$DIR/template.html"
# Render txt2tags into html file
# Arguments:
# 1. txt2tags source file, e.g. download/index.t2t
# 2. html target file, e.g. download/index.html
function render_t2t_html {
t2t="$1"
html="$2"
tmp="$2.tmp"
relroot="$( dirname $t2t | sed -E 's/^.\///' | sed -E 's/[^/]+/../g' )"
# First render with txt2tags to handle pre/post processing
txt2tags \
--target=html \
--no-headers \
--quiet \
--outfile="$tmp" \
--infile="$t2t"
# Replace <A NAME="toc3"></A> with <div id="toc3"></div> so that Pandoc retains it
# Do this for both cases since BSD sed doesn't support /i
sed -i.bak "s/<a name=\"\(.*\)\"><\/a>/<div id=\"\1\"><\/div>/" "$tmp"
sed -i.bak "s/<A NAME=\"\(.*\)\"><\/A>/<div id=\"\1\"><\/div>/" "$tmp"
rm -f "$tmp.bak"
# Capture first 3 lines of t2t file: title, author, date
# Documentation here: https://txt2tags.org/userguide/headerarea
l1=$(head -n 1 "$t2t")
l2=$(tail -n+2 "$t2t" | head -n 1)
l3=$(tail -n+3 "$t2t" | head -n 1)
title=
author=
date=
if [ -n "$l1" ] ; then
title="$l1"
if [ -n "$l2" ] ; then author="$l2" ; fi
if [ -n "$l3" ] ; then date="$l3" ; fi
fi
done
# Run txt2tag's HTML through Pandoc for cleanup
pandoc \
--from=html \
--to=html5 \
--standalone \
--template="$template" \
--variable="lang:en" \
--variable="rel-root:$relroot" \
--metadata="title:$title" \
--metadata="author:$author" \
--metadata="date:$date" \
"$tmp" \
--output="$html"
rm -f "$tmp"
# Final post-processing
if [ -f "$html" ] ; then
sed -i.bak "s/<table/<table class=\"table\"/" "$html" && rm "$html.bak"
echo "$html"
fi
}
# Render markdown into html file
# Arguments:
# 1. markdown source file, e.g. download/index.md
# 2. html target file, e.g. download/index.html
function render_md_html {
md="$1"
html="$2"
relroot="$( dirname $md | sed -E 's/^.\///' | sed -E 's/[^/]+/../g' )"
# Look for `show-toc: true` in metadata (first ten lines of file)
if head -n 10 "$md" | grep --quiet 'show-toc: true' ; then
tocflag='--table-of-contents'
else
tocflag=''
fi
pandoc \
--from=markdown \
--to=html5 \
--standalone \
$tocflag \
--template="$template" \
--variable="lang:en" \
--variable="rel-root:$relroot" \
"$md" \
--output="$html"
# Final post-processing
if [ -f "$html" ] ; then
# add "table" class to tables
sed -i.bak "s/<table/<table class=\"table\"/" "$html"
# rewrite anchors that Pandoc 1.16 ignores: [content]{#anchor} -> <span id="anchor">content</span>
sed -i.bak -E "s/\[(.*)\]\{#(.+)\}/<span id=\"\2\">\1<\/span>/" "$html"
rm -f "$html.bak"
echo "$html"
fi
}
# Main entry point
# Script can be run in one of two modes:
if [ $# -gt 0 ] ; then
# Render specific file(s) from args, ignoring dates
for file in "$@" ; do
ext="${file##*.}"
html="${file%.$ext}.html"
case $ext in
"md")
render_md_html "$file" "$html"
;;
"t2t")
render_t2t_html "$file" "$html"
;;
esac
done
else
# Render all files found in cwd and deeper if source is newer
find . -name '*.t2t' | while read file ; do
html="${file%.t2t}.html"
if [ "$file" -nt "$html" ] || [ "$template" -nt "$html" ] ; then
render_t2t_html "$file" "$html"
fi
done
find . -name '*.md' | while read file ; do
if [[ "$file" == *"README.md" ]] ; then continue ; fi
html="${file%.md}.html"
if [ "$file" -nt "$html" ] || [ "$template" -nt "$html" ] ; then
render_md_html "$file" "$html"
fi
done
fi

View File

@@ -17,10 +17,7 @@ h1 img.nofloat { float: none; }
img.right { float: right; }
ol.languages {
display: flex;
flex-direction: column;
flex-wrap: wrap;
height: 12em;
column-width: 12em;
}
.grow {

18
debian/changelog vendored
View File

@@ -1,3 +1,21 @@
gf (3.10.3-1) xenial bionic cosmic; urgency=low
* GF 3.10.3
-- Thomas Hallgren <hallgren@chalmers.se> Fri, 5 Mar 2019 19:30:00 +0100
gf (3.10-2) xenial bionic cosmic; urgency=low
* GF 3.10
-- Thomas Hallgren <hallgren@chalmers.se> Fri, 5 Mar 2019 16:00:00 +0100
gf (3.10-1) xenial bionic cosmic; urgency=low
* GF 3.10
-- Thomas Hallgren <hallgren@chalmers.se> Fri, 2 Dec 2018 15:00:00 +0100
gf (3.9-1) vivid xenial zesty; urgency=low
* GF 3.9

2
debian/control vendored
View File

@@ -3,7 +3,7 @@ Section: devel
Priority: optional
Maintainer: Thomas Hallgren <hallgren@chalmers.se>
Standards-Version: 3.9.2
Build-Depends: debhelper (>= 5), haskell-platform (>= 2011.2.0.1), libghc-haskeline-dev, libghc-mtl-dev, libghc-json-dev, autoconf, automake, libtool-bin, python-dev, java-sdk, txt2tags
Build-Depends: debhelper (>= 5), haskell-platform (>= 2011.2.0.1), libghc-haskeline-dev, libghc-mtl-dev, libghc-json-dev, autoconf, automake, libtool-bin, python-dev, java-sdk, txt2tags, pandoc
Homepage: http://www.grammaticalframework.org/
Package: gf

33
debian/rules vendored Normal file → Executable file
View File

@@ -13,19 +13,6 @@
override_dh_shlibdeps:
dh_shlibdeps --dpkg-shlibdeps-params=--ignore-missing-info
override_dh_auto_build:
cd src/runtime/python && EXTRA_INCLUDE_DIRS=$(CURDIR)/src/runtime/c EXTRA_LIB_DIRS=$(CURDIR)/src/runtime/c/.libs python setup.py build
cd src/runtime/java && make CFLAGS="-I$(CURDIR)/src/runtime/c -L$(CURDIR)/src/runtime/c/.libs" INSTALL_PATH=/usr/lib
echo LD_LIBRARY_PATH=$$LD_LIBRARY_PATH:$(CURDIR)/src/runtime/c/.libs
LD_LIBRARY_PATH=$$LD_LIBRARY_PATH:$(CURDIR)/src/runtime/c/.libs cabal build
make html
override_dh_auto_clean:
rm -fr dist/build
-cd src/runtime/python && rm -fr build
-cd src/runtime/java && make clean
-cd src/runtime/c && make clean
override_dh_auto_configure:
cd src/runtime/c && bash setup.sh configure --prefix=/usr
cd src/runtime/c && bash setup.sh build
@@ -33,13 +20,31 @@ override_dh_auto_configure:
cabal install --only-dependencies
cabal configure --prefix=/usr -fserver -fc-runtime --extra-lib-dirs=$(CURDIR)/src/runtime/c/.libs --extra-include-dirs=$(CURDIR)/src/runtime/c
SET_LDL=LD_LIBRARY_PATH=$$LD_LIBRARY_PATH:$(CURDIR)/src/runtime/c/.libs
override_dh_auto_build:
cd src/runtime/python && EXTRA_INCLUDE_DIRS=$(CURDIR)/src/runtime/c EXTRA_LIB_DIRS=$(CURDIR)/src/runtime/c/.libs python setup.py build
cd src/runtime/java && make CFLAGS="-I$(CURDIR)/src/runtime/c -L$(CURDIR)/src/runtime/c/.libs" INSTALL_PATH=/usr/lib
echo $(SET_LDL)
$(SET_LDL) cabal build # builds gf, fails to build example grammars
PATH=$(CURDIR)/dist/build/gf:$$PATH && make -C ../gf-rgl build
GF_LIB_PATH=$(CURDIR)/../gf-rgl/dist $(SET_LDL) cabal build # have RGL now, ok to build example grammars
make html
override_dh_auto_install:
LD_LIBRARY_PATH=$$LD_LIBRARY_PATH:$(CURDIR)/src/runtime/c/.libs cabal copy --destdir=$(CURDIR)/debian/gf
$(SET_LDL) cabal copy --destdir=$(CURDIR)/debian/gf # creates www directory
export GF_LIB_PATH="$$(dirname $$(find "$(CURDIR)/debian/gf" -name www))/lib" && echo "GF_LIB_PATH=$$GF_LIB_PATH" && mkdir -p "$$GF_LIB_PATH" && make -C ../gf-rgl copy
cd src/runtime/c && bash setup.sh copy prefix=$(CURDIR)/debian/gf/usr
cd src/runtime/python && python setup.py install --prefix=$(CURDIR)/debian/gf/usr
cd src/runtime/java && make INSTALL_PATH=$(CURDIR)/debian/gf/usr/lib install
D="`find debian/gf -name site-packages`" && [ -n "$$D" ] && cd $$D && cd .. && mv site-packages dist-packages
override_dh_auto_clean:
rm -fr dist/build
-cd src/runtime/python && rm -fr build
-cd src/runtime/java && make clean
-cd src/runtime/c && make clean
override_dh_auto_test:
ifneq (nocheck,$(filter nocheck,$(DEB_BUILD_OPTIONS)))
true

View File

@@ -1,18 +1,3 @@
resource:
gfdoc -txt2 ../lib/resource-1.0/abstract/*.gf
gfdoc -txt2 ../lib/resource-1.0/*/Paradigms*.gf
txt2tags --toc resource.txt
# cat resource-preamble resource.tex >final-resource.tex
sed -i 's/\\docum/%\\docum/g' resource.tex
sed -i 's/ion\*{/ion{/g' resource.tex
sed -i 's/\\paragraph{}//g' resource.tex
sed -i 's/}\\\\/}/g' resource.tex
cat resource-preamble resource.tex >resource.tmp
mv resource.tmp resource.tex
latex resource.tex
latex resource.tex
dvipdf resource.dvi
gf-help-full.txt::
{ echo ; echo ; echo ; } > $@
echo help -full -t2t | gf -run >> $@

551
doc/error-messages.txt Normal file
View File

@@ -0,0 +1,551 @@
Compiler.hs
mainGFC :: Options -> [FilePath] -> IO ()
_ | null fs -> fail $ "No input files."
_ | all (extensionIs ".pgf") fs -> unionPGFFiles opts fs
_ -> fail $ "Don't know what to do with these input files: " ++ unwords fs)
----------------------------------------
Compile.hs
compileModule
case length file1s of
0 -> raise (render ("Unable to find: " $$ nest 2 candidates))
1 -> do return $ head file1s
_ -> do putIfVerb opts1 ("matched multiple candidates: " +++ show file1s)
return $ head file1s
else raise (render ("File" <+> file <+> "does not exist"))
---------------------------------------
Grammar.Lexer.x
token :: P Token
AlexError (AI pos _ _) -> PFailed pos "lexical error"
---------------------------------------
Grammar.Parser.y
happyError = fail "syntax error"
tryLoc (c,mty,Just e) = return (c,(mty,e))
tryLoc (c,_ ,_ ) = fail ("local definition of" +++ showIdent c +++ "without value")
mkR [] = return $ RecType [] --- empty record always interpreted as record type
mkR fs@(f:_) =
case f of
(lab,Just ty,Nothing) -> mapM tryRT fs >>= return . RecType
_ -> mapM tryR fs >>= return . R
where
tryRT (lab,Just ty,Nothing) = return (ident2label lab,ty)
tryRT (lab,_ ,_ ) = fail $ "illegal record type field" +++ showIdent lab --- manifest fields ?!
tryR (lab,mty,Just t) = return (ident2label lab,(mty,t))
tryR (lab,_ ,_ ) = fail $ "illegal record field" +++ showIdent lab
---------------------------------------
ModDeps.hs
mkSourceGrammar :: [SourceModule] -> Err SourceGrammar
deplist <- either
return
(\ms -> Bad $ "circular modules" +++ unwords (map show ms)) $
checkUniqueImportNames :: [Ident] -> SourceModInfo -> Err ()
test ms = testErr (all (`notElem` ns) ms)
("import names clashing with module names among" +++ unwords (map prt ms))
moduleDeps :: [SourceModule] -> Err Dependencies
deps (c,m) = errIn ("checking dependencies of module" +++ prt c) $ case mtype m of
MTConcrete a -> do
am <- lookupModuleType gr a
testErr (mtype am == MTAbstract) "the of-module is not an abstract syntax"
testErr (all (compatMType ety . mtype) ests) "inappropriate extension module type"
---------------------------------------
Update.hs
buildAnyTree
Just i -> case unifyAnyInfo m i j of
Ok k -> go (Map.insert c k map) is
Bad _ -> fail $ render ("conflicting information in module"<+>m $$
nest 4 (ppJudgement Qualified (c,i)) $$
"and" $+$
nest 4 (ppJudgement Qualified (c,j)))
extendModule
unless (sameMType (mtype m) (mtype mo))
(checkError ("illegal extension type to module" <+> name))
rebuildModule
unless (null is || mstatus mi == MSIncomplete)
(checkError ("module" <+> i <+>
"has open interfaces and must therefore be declared incomplete"))
unless (isModRes m1)
(checkError ("interface expected instead of" <+> i0))
js' <- extendMod gr False ((i0,m1), isInherited mincl) i (jments mi)
unless (stat' == MSComplete || stat == MSIncomplete)
(checkError ("module" <+> i <+> "remains incomplete"))
extendMod
checkError ("cannot unify the information" $$
nest 4 (ppJudgement Qualified (c,i)) $$
"in module" <+> name <+> "with" $$
nest 4 (ppJudgement Qualified (c,j)) $$
"in module" <+> base)
unifyAnyInfo
(ResValue (L l1 t1), ResValue (L l2 t2))
| t1==t2 -> return (ResValue (L l1 t1))
| otherwise -> fail ""
(AnyInd b1 m1, AnyInd b2 m2) -> do
testErr (b1 == b2) $ "indirection status"
testErr (m1 == m2) $ "different sources of indirection"
unifAbsDefs _ _ = fail ""
----------------------------------
Rename.hs
renameIdentTerm'
_ -> case lookupTreeManyAll showIdent opens c of
[f] -> return (f c)
[] -> alt c ("constant not found:" <+> c $$
"given" <+> fsep (punctuate ',' (map fst qualifs)))
ts@(t:_) -> do checkWarn ("atomic term" <+> ppTerm Qualified 0 t0 $$
"conflict" <+> hsep (punctuate ',' (map (ppTerm Qualified 0) ts)) $$
"given" <+> fsep (punctuate ',' (map fst qualifs)))
return t
renameInfo
renLoc ren (L loc x) =
checkInModule cwd mi loc ("Happened in the renaming of" <+> i) $ do
renameTerm
| otherwise -> checks [ renid' (Q (MN r,label2ident l)) -- .. and qualified expression second.
, renid' t >>= \t -> return (P t l) -- try as a constant at the end
, checkError ("unknown qualified constant" <+> trm)
]
renamePattern env patt =
do r@(p',vs) <- renp patt
let dupl = vs \\ nub vs
unless (null dupl) $ checkError (hang ("[C.4.13] Pattern is not linear:") 4
patt)
return r
case c' of
Q d -> renp $ PM d
_ -> checkError ("unresolved pattern" <+> patt)
Q _ -> checkError ("data constructor expected but" <+> ppTerm Qualified 0 c' <+> "is found instead")
_ -> checkError ("unresolved data constructor" <+> ppTerm Qualified 0 c')
PM c -> do
x <- renid (Q c)
c' <- case x of
(Q c') -> return c'
_ -> checkError ("not a pattern macro" <+> ppPatt Qualified 0 patt)
PV x -> checks [ renid' (Vr x) >>= \t' -> case t' of
QC c -> return (PP c [],[])
_ -> checkError (pp "not a constructor")
, return (patt, [x])
-----------------------------------
CheckGrammar.hs
checkRestrictedInheritance :: FilePath -> SourceGrammar -> SourceModule -> Check ()
let illegals = [(f,is) |
(f,cs) <- allDeps, incld f, let is = filter illegal cs, not (null is)]
case illegals of
[] -> return ()
cs -> checkWarn ("In inherited module" <+> i <> ", dependence of excluded constants:" $$
nest 2 (vcat [f <+> "on" <+> fsep is | (f,is) <- cs]))
checkCompleteGrammar :: Options -> FilePath -> Grammar -> Module -> Module -> Check Module
case info of
CncCat (Just (L loc (RecType []))) _ _ _ _ -> return (foldr (\_ -> Abs Explicit identW) (R []) cxt)
_ -> Bad "no def lin"
where noLinOf c = checkWarn ("no linearization of" <+> c)
Ok (CncCat Nothing md mr mp mpmcfg) -> do
checkWarn ("no linearization type for" <+> c <> ", inserting default {s : Str}")
return $ updateTree (c,CncCat (Just (L NoLoc defLinType)) md mr mp mpmcfg) js
_ -> do
checkWarn ("no linearization type for" <+> c <> ", inserting default {s : Str}")
_ -> do checkWarn ("function" <+> c <+> "is not in abstract")
Ok (_,AbsFun {}) ->
checkError ("lincat:"<+>c<+>"is a fun, not a cat")
-}
_ -> do checkWarn ("category" <+> c <+> "is not in abstract")
checkInfo :: Options -> FilePath -> SourceGrammar -> SourceModule -> Ident -> Info -> Check Info
(Just (L loct ty), Nothing) -> do
chIn loct "operation" $
checkError (pp "No definition given to the operation")
ResOverload os tysts -> chIn NoLoc "overloading" $ do
checkUniq xss = case xss of
x:y:xs
| x == y -> checkError $ "ambiguous for type" <+>
ppType (mkFunType (tail x) (head x))
compAbsTyp g t = case t of
Vr x -> maybe (checkError ("no value given to variable" <+> x)) return $ lookup x g
checkReservedId x =
when (isReservedWord x) $
checkWarn ("reserved word used as identifier:" <+> x)
--------------------------------
TypeCheck/Abstract.hs
grammar2theory :: SourceGrammar -> Theory
Bad s -> case lookupCatContext gr m f of
Ok cont -> return $ cont2val cont
_ -> Bad s
--------------------------------
TypeCheck/ConcreteNew.hs
-- Concrete.hs has all its code commented out
--------------------------------
TypeCheck/RConcrete.hs
-- seems to be used more than ConcreteNew
computeLType :: SourceGrammar -> Context -> Type -> Check Type
AdHocOverload ts -> do
over <- getOverload gr g (Just typeType) t
case over of
Just (tr,_) -> return tr
_ -> checkError ("unresolved overloading of constants" <+> ppTerm Qualified 0 t)
inferLType :: SourceGrammar -> Context -> Term -> Check (Term, Type)
Q (m,ident) | isPredef m -> termWith trm $ case typPredefined ident of
Nothing -> checkError ("unknown in Predef:" <+> ident)
Q ident -> checks [
checkError ("cannot infer type of constant" <+> ppTerm Unqualified 0 trm)
]
QC ident -> checks [
checkError ("cannot infer type of canonical constant" <+> ppTerm Unqualified 0 trm)
]
Vr ident -> termWith trm $ checkLookup ident g
AdHocOverload ts -> do
_ -> checkError ("unresolved overloading of constants" <+> ppTerm Qualified 0 trm)
App f a -> do
case fty' of
Prod bt z arg val -> do
_ -> checkError ("A function type is expected for" <+> ppTerm Unqualified 0 f <+> "instead of type" <+> ppType fty)
S f x -> do
_ -> checkError ("table lintype expected for the table in" $$ nest 2 (ppTerm Unqualified 0 trm))
P t i -> do
Nothing -> checkError ("unknown label" <+> i <+> "in" $$ nest 2 (ppTerm Unqualified 0 ty'))
_ -> checkError ("record type expected for:" <+> ppTerm Unqualified 0 t $$
" instead of the inferred:" <+> ppTerm Unqualified 0 ty')
R r -> do
checkCond ("cannot infer type of record" $$ nest 2 (ppTerm Unqualified 0 trm)) (length ts == length fsts)
T ti pts -> do -- tries to guess: good in oper type inference
[] -> checkError ("cannot infer table type of" <+> ppTerm Unqualified 0 trm)
---- hack from Rename.identRenameTerm, to live with files with naming conflicts 18/6/2007
Strs (Cn c : ts) | c == cConflict -> do
checkWarn ("unresolved constant, could be any of" <+> hcat (map (ppTerm Unqualified 0) ts))
ExtR r s -> do
case (rT', sT') of
(RecType rs, RecType ss) -> do
_ -> checkError ("records or record types expected in" <+> ppTerm Unqualified 0 trm)
_ -> checkError ("cannot infer lintype of" <+> ppTerm Unqualified 0 trm)
getOverload :: SourceGrammar -> Context -> Maybe Type -> Term -> Check (Maybe (Term,Type))
matchOverload f typs ttys = do
checkWarn $ "ignoring lock fields in resolving" <+> ppTerm Unqualified 0 ot $$
"for" $$
nest 2 (showTypes tys) $$
"using" $$
nest 2 (showTypes pre)
([],[]) -> do
checkError $ "no overload instance of" <+> ppTerm Unqualified 0 f $$
"for" $$
nest 2 stysError $$
"among" $$
nest 2 (vcat stypsError) $$
maybe empty (\x -> "with value type" <+> ppType x) mt
([],[(val,fun)]) -> do
checkWarn ("ignoring lock fields in resolving" <+> ppTerm Unqualified 0 ot)
(nps1,nps2) -> do
checkWarn $ "ambiguous overloading of" <+> ppTerm Unqualified 0 f <+>
---- "with argument types" <+> hsep (map (ppTerm Qualified 0) tys) $$
"resolved by selecting the first of the alternatives" $$
nest 2 (vcat [ppTerm Qualified 0 fun | (_,ty,fun) <- vfs1 ++ if null vfs1 then vfs2 else []])
case [(mkApp fun tts,val) | (val,fun) <- nps1 ++ nps2] of
[] -> checkError $ "no alternatives left when resolving" <+> ppTerm Unqualified 0 f
checkLType :: SourceGrammar -> Context -> Term -> Type -> Check (Term, Type)
Abs bt x c -> do
case typ of
Prod bt' z a b -> do
_ -> checkError $ "function type expected instead of" <+> ppType typ
AdHocOverload ts -> do
_ -> checkError ("unresolved overloading of constants" <+> ppTerm Qualified 0 trm)
T _ [] ->
checkError ("found empty table in type" <+> ppTerm Unqualified 0 typ)
T _ cs -> case typ of
else checkWarn ("patterns never reached:" $$
nest 2 (vcat (map (ppPatt Unqualified 0) ps)))
_ -> checkError $ "table type expected for table instead of" $$ nest 2 (ppType typ)
V arg0 vs ->
if length vs1 == length vs
then return ()
else checkError $ "wrong number of values in table" <+> ppTerm Unqualified 0 trm
R r -> case typ of --- why needed? because inference may be too difficult
RecType rr -> do
_ -> checkError ("record type expected in type checking instead of" $$ nest 2 (ppTerm Unqualified 0 typ))
ExtR r s -> case typ of
case trm' of
RecType _ -> termWith trm' $ return typeType
ExtR (Vr _) (RecType _) -> termWith trm' $ return typeType
-- ext t = t ** ...
_ -> checkError ("invalid record type extension" <+> nest 2 (ppTerm Unqualified 0 trm))
case typ2 of
RecType ss -> return $ map fst ss
_ -> checkError ("cannot get labels from" $$ nest 2 (ppTerm Unqualified 0 typ2))
_ -> checkError ("record extension not meaningful for" <+> ppTerm Unqualified 0 typ)
S tab arg -> checks [ do
_ -> checkError ("table type expected for applied table instead of" <+> ppType ty')
_ -> do
(trm',ty') <- inferLType gr g trm
termWith trm' $ checkEqLType gr g typ ty' trm'
checkM rms (l,ty) = case lookup l rms of
_ -> checkError $
if isLockLabel l
then let cat = drop 5 (showIdent (label2ident l))
in ppTerm Unqualified 0 (R rms) <+> "is not in the lincat of" <+> cat <>
"; try wrapping it with lin" <+> cat
else "cannot find value for label" <+> l <+> "in" <+> ppTerm Unqualified 0 (R rms)
checkEqLType :: SourceGrammar -> Context -> Type -> Type -> Term -> Check Type
False -> checkError $ s <+> "type of" <+> ppTerm Unqualified 0 trm $$
"expected:" <+> ppTerm Qualified 0 t $$ -- ppqType t u $$
"inferred:" <+> ppTerm Qualified 0 u -- ppqType u t
checkIfEqLType :: SourceGrammar -> Context -> Type -> Type -> Term -> Check (Bool,Type,Type,String)
Ok lo -> do
checkWarn $ "missing lock field" <+> fsep lo
missingLock g t u = case (t,u) of
_:_ -> Bad $ render ("missing record fields:" <+> fsep (punctuate ',' (others)))
pattContext :: SourceGrammar -> Context -> Type -> Patt -> Check Context
checkCond ("wrong number of arguments for constructor in" <+> ppPatt Unqualified 0 p)
(length cont == length ps)
PR r -> do
_ -> checkError ("record type expected for pattern instead of" <+> ppTerm Unqualified 0 typ')
PAlt p' q -> do
g1 <- pattContext env g typ p'
g2 <- pattContext env g typ q
let pts = nub ([x | pt@(_,x,_) <- g1, notElem pt g2] ++ [x | pt@(_,x,_) <- g2, notElem pt g1])
checkCond
("incompatible bindings of" <+>
fsep pts <+>
"in pattern alterantives" <+> ppPatt Unqualified 0 p) (null pts)
return g1 -- must be g1 == g2
noBind typ p' = do
co <- pattContext env g typ p'
if not (null co)
then checkWarn ("no variable bound inside pattern" <+> ppPatt Unqualified 0 p)
>> return []
else return []
checkLookup :: Ident -> Context -> Check Type -- used for looking up Vr x type in context
[] -> checkError ("unknown variable" <+> x)
-------------------------------
Grammar/Lookup.hs
lookupIdent :: ErrorMonad m => Ident -> BinTree Ident b -> m b
Bad _ -> raise ("unknown identifier" +++ showIdent c)
lookupResDefLoc
_ -> raise $ render (c <+> "is not defined in resource" <+> m)
lookupResType :: ErrorMonad m => Grammar -> QIdent -> m Type
_ -> raise $ render (c <+> "has no type defined in resource" <+> m)
lookupOverloadTypes :: ErrorMonad m => Grammar -> QIdent -> m [(Term,Type)]
_ -> raise $ render (c <+> "has no types defined in resource" <+> m)
lookupOverload :: ErrorMonad m => Grammar -> QIdent -> m [([Type],(Type,Term))]
_ -> raise $ render (c <+> "is not an overloaded operation")
lookupParamValues :: ErrorMonad m => Grammar -> QIdent -> m [Term]
case info of
ResParam _ (Just pvs) -> return pvs
_ -> raise $ render (ppQIdent Qualified c <+> "has no parameter values defined")
allParamValues :: ErrorMonad m => Grammar -> Type -> m [Term]
_ -> raise (render ("cannot find parameter values for" <+> ptyp))
lookupFunType :: ErrorMonad m => Grammar -> ModuleName -> Ident -> m Type
_ -> raise (render ("cannot find type of" <+> c))
lookupCatContext :: ErrorMonad m => Grammar -> ModuleName -> Ident -> m Context
_ -> raise (render ("unknown category" <+> c))
-------------------------
PatternMatch.hs
matchPattern :: ErrorMonad m => [(Patt,rhs)] -> Term -> m (rhs, Substitution)
if not (isInConstantForm term)
then raise (render ("variables occur in" <+> pp term))
findMatch :: ErrorMonad m => [([Patt],rhs)] -> [Term] -> m (rhs, Substitution)
[] -> raise (render ("no applicable case for" <+> hsep (punctuate ',' terms)))
(patts,_):_ | length patts /= length terms ->
raise (render ("wrong number of args for patterns :" <+> hsep patts <+>
"cannot take" <+> hsep terms))
tryMatch :: (Patt, Term) -> Err [(Ident, Term)]
(PNeg p',_) -> case tryMatch (p',t) of
Bad _ -> return []
_ -> raise (render ("no match with negative pattern" <+> p))
---------------------------------------------
Compile.Optimize.hs
mkLinDefault :: SourceGrammar -> Type -> Err Term
_ -> Bad (render ("no parameter values given to type" <+> ppQIdent Qualified p))
_ -> Bad (render ("linearization type field cannot be" <+> typ))
mkLinReference :: SourceGrammar -> Type -> Err Term
[] -> Bad "no string"
---------------------------------------------
Compile.Compute.Concrete.hs
nfx env@(GE _ _ _ loc) t = do
Left i -> fail ("variable #"++show i++" is out of scope")
var :: CompleteEnv -> Ident -> Err OpenValue
var env x = maybe unbound pick' (elemIndex x (local env))
where
unbound = fail ("Unknown variable: "++showIdent x)
pick' i = return $ \ vs -> maybe (err i vs) ok (pick i vs)
err i vs = bug $ "Stack problem: "++showIdent x++": "
++unwords (map showIdent (local env))
++" => "++show (i,length vs)
resource env (m,c) =
where e = fail $ "Not found: "++render m++"."++showIdent c
extR t vv =
(VRecType rs1, VRecType rs2) ->
case intersect (map fst rs1) (map fst rs2) of
[] -> VRecType (rs1 ++ rs2)
ls -> error $ "clash"<+>show ls
(v1,v2) -> error $ "not records" $$ show v1 $$ show v2
where
error explain = ppbug $ "The term" <+> t
<+> "is not reducible" $$ explain
glue env (v1,v2) = glu v1 v2
ppL loc (hang "unsupported token gluing:" 4
(Glue (vt v1) (vt v2)))
strsFromValue :: Value -> Err [Str]
_ -> fail ("cannot get Str from value " ++ show t)
match loc cs v =
case value2term loc [] v of
Left i -> bad ("variable #"++show i++" is out of scope")
Right t -> err bad return (matchPattern cs t)
where
bad = fail . ("In pattern matching: "++)
inlinePattMacro p =
VPatt p' -> inlinePattMacro p'
_ -> ppbug $ hang "Expected pattern macro:" 4
linPattVars p =
if null dups
then return pvs
else fail.render $ hang "Pattern is not linear:" 4 (ppPatt Unqualified 0 p)
---------------------------------------------
Compile.Compute.Abstract.hs
---------------------------------------------
PGF.Linearize.hs
bracketedLinearize :: PGF -> Language -> Tree -> [BracketedString]
cnc = lookMap (error "no lang") lang (concretes pgf)
---------------------------------------------
PGF.TypeCheck.hs
ppTcError :: TcError -> Doc
ppTcError (UnknownCat cat) = text "Category" <+> ppCId cat <+> text "is not in scope"
ppTcError (UnknownFun fun) = text "Function" <+> ppCId fun <+> text "is not in scope"
ppTcError (WrongCatArgs xs ty cat m n) = text "Category" <+> ppCId cat <+> text "should have" <+> int m <+> text "argument(s), but has been given" <+> int n $$
text "In the type:" <+> ppType 0 xs ty
ppTcError (TypeMismatch xs e ty1 ty2) = text "Couldn't match expected type" <+> ppType 0 xs ty1 $$
text " against inferred type" <+> ppType 0 xs ty2 $$
text "In the expression:" <+> ppExpr 0 xs e
ppTcError (NotFunType xs e ty) = text "A function type is expected for the expression" <+> ppExpr 0 xs e <+> text "instead of type" <+> ppType 0 xs ty
ppTcError (CannotInferType xs e) = text "Cannot infer the type of expression" <+> ppExpr 0 xs e
ppTcError (UnresolvedMetaVars xs e ms) = text "Meta variable(s)" <+> fsep (List.map ppMeta ms) <+> text "should be resolved" $$
text "in the expression:" <+> ppExpr 0 xs e
ppTcError (UnexpectedImplArg xs e) = braces (ppExpr 0 xs e) <+> text "is implicit argument but not implicit argument is expected here"
ppTcError (UnsolvableGoal xs metaid ty)= text "The goal:" <+> ppMeta metaid <+> colon <+> ppType 0 xs ty $$
text "cannot be solved"

View File

@@ -1,16 +1,8 @@
GF Developers Guide
Authors: Björn Bringert, Krasimir Angelov and Thomas Hallgren
Last update: %%mtime(%F, %H:%M)
% NOTE: this is a txt2tags file.
% Create an html file from this file using:
% txt2tags -t html gf-developers.t2t
2018-07-26
%!style:../css/style.css
%!target:html
%!options(html): --toc
%!encoding:utf-8
%!postproc(html): <H1> <H1><a href="../"><IMG src="../doc/Logos/gf0.png"></a>
== Before you start ==
@@ -63,18 +55,6 @@ Other required tools included in the Haskell Platform are
and
[Happy http://www.haskell.org/happy/].
%=== Darcs ===
%
%To get the GF source code, you also need //Darcs//, version 2 or later.
%Darcs 2.10 is recommended (July 2015).
%
%//Darcs//
%is a distributed version control system, see http://darcs.net/ for
%more information. There are precompiled packages for many platforms
%available and source code if you want to compile it yourself. Darcs
%is also written in Haskell and so you can use GHC to compile it.
=== Git ===
To get the GF source code, you also need //Git//.
@@ -425,13 +405,13 @@ There is also ``make build``, ``make copy`` and ``make clean`` which do what you
=== Advanced ===
For advanced build options, call the Haskell build script directly:
```
$ runghc Make.hs ...
$ runghc Setup.hs ...
```
For more details see the [README https://github.com/GrammaticalFramework/gf-rgl/blob/master/README.md].
=== Haskell-free ===
If you do not have Haskell installed, you can use the simple build script ``Make.sh``
(or ``Make.bat`` for Windows).
If you do not have Haskell installed, you can use the simple build script ``Setup.sh``
(or ``Setup.bat`` for Windows).
== Creating binary distribution packages ==

View File

@@ -1,12 +1,6 @@
Editor modes & IDE integration for GF
%!style:../css/style.css
%!options(html): --toc
%!postproc(html): <TITLE> <meta name = "viewport" content = "width = device-width"><TITLE>
%!encoding:utf-8
%!postproc(html): <H1> <H1><a href="../"><IMG src="../doc/Logos/gf0.png"></a>
We collect GF modes for various editors on this page. Contributions are
welcome!

View File

@@ -1,91 +0,0 @@
Grammatical Framework: Frequently Asked Quuestions
Aarne Ranta
%%date(%c)
% NOTE: this is a txt2tags file.
% Create an html file from this file using:
% txt2tags gf-bibliography.t2t
%!style:../css/style.css
%!target:html
%!options(html): --toc
%!postproc(html): <TITLE> <meta name = "viewport" content = "width = device-width"><TITLE>
%!postproc(html): #BR <br>
%!encoding:utf-8
%!postproc(html): <H1> <H1><a href="../"><IMG src="../doc/Logos/gf0.png"></a>
===What has been done with GF?===
**Translation**: systems with any number of parallel languages, with input in one language and output in all the others.
**Natural language generation** (NLG): translation from a formal language to natural languages.
**Ontology verbalization** is a special case of NLG.
**Language training**: grammar and vocabulary training systems.
**Human-computer interaction**: natural language interfaces, spoken dialogue systems.
**Linguistics**: comparisons between languages.
===What parts does GF have?===
A **grammar compiler**, used for compiling grammars to parsing, generation, and translation code.
A **run-time system**, used for parsing, generation and translation. The run-time system is available in several languages:
Haskell, Java, C, C++, Javascript, and Python. The point with this is that you can include GF-based parsing and generation in
larger programs written in any of these languages.
A **resource grammar library**, containing the morphology and basic syntax of currently 26 languages.
A **web application toolkit**, containing server-side (Haskell) and client-side (Javascript) libraries.
An **integrated development environment**, the GF-Eclipse plug-in.
A **shell**, i.e. a command interpreter for testing and developing GF grammars. This is the program started by the command ``gf`` in a terminal.
===Is GF open-source?===
===Can I use GF for commercial applications?===
Yes. Those parts of GF that you will need to distribute - the run-time system and the libraries - are licensed under LGPL and BSD; it's up to you to choose which.
===When was GF started?===
===Where does the name GF come from?===
GF = Grammatical Framework = LF + concrete syntax
LF = Logical Framework
Logical Frameworks are implementations of type theory, which have been built since the 1980's to support formalized mathematics. GF has its roots in
type theory, which is widely used in the semantics of natural language. Some of these ideas were first implemented in ALF, Another Logical Framework,
in 1992; the book //Type-Theoretical Grammar// (by A. Ranta, OUP 1994) has a chapter and an appendix on this. The first implementations did not have
a parser, and GF proper, started in 1998, was an implementation of yet another LF together with concrete syntax supporting generation and parsing.
Grammatical Framework was a natural name for this. We tried to avoid it in the beginning, because it sounded pretentious in its generality. But the
name was just too natural to be avoided.
===Is GF backward compatible?===
===Do I need Haskell to use GF?===
No. GF is a language of its own, and you don't need to know Haskell. And if you download the GF binary, you don't need any Haskell tools. But if you want to
become a GF developer, then it's better you install GF from the latest source, and then you need the GHC Haskell compiler to compile GF. But even then, you
don't need to know Haskell yourself.
===What is a lock field?===

View File

@@ -68,9 +68,9 @@ metavariables and the type of the expression.
Prints a set of strings in the .dot format (the graphviz format).
The graph can be saved in a file by the wf command as usual.
If the -view flag is defined, the graph is saved in a temporary file
which is processed by graphviz and displayed by the program indicated
by the flag. The target format is postscript, unless overridden by the
flag -format.
which is processed by 'dot' (graphviz) and displayed by the program indicated
by the view flag. The target format is png, unless overridden by the
flag -format. Results from multiple trees are combined to pdf with convert (ImageMagick).
- Options:
@@ -151,6 +151,7 @@ of a pipe.
| ``-one`` | pick the first strings, if there is any, from records and tables
| ``-table`` | show all strings labelled by parameters
| ``-unqual`` | hide qualifying module names
| ``-trace`` | trace computations
#NORMAL
@@ -242,7 +243,7 @@ and thus cannot be a part of a pipe.
====e = empty====
#NOINDENT
``e`` = ``empty``: //empty the environment.//
``e`` = ``empty``: //empty the environment (except the command history).//
#TINY
@@ -281,6 +282,19 @@ but the resulting .gf file must be imported separately.
#NORMAL
#VSPACE
====eh = execute_history====
#NOINDENT
``eh`` = ``execute_history``: //read commands from a file and execute them.//
#TINY
- Syntax: ``eh FILE``
#NORMAL
#VSPACE
====gr = generate_random====
@@ -434,12 +448,14 @@ sequences; see example.
| ``-list`` | show all forms and variants, comma-separated on one line (cf. l -all)
| ``-multi`` | linearize to all languages (default)
| ``-table`` | show all forms labelled by parameters
| ``-tabtreebank`` | show the tree and its linearizations on a tab-separated line
| ``-treebank`` | show the tree and tag linearizations with language names
| ``-bind`` | bind tokens separated by Prelude.BIND, i.e. &+
| ``-chars`` | lexer that makes every non-space character a token
| ``-from_amharic`` | from unicode to GF Amharic transliteration
| ``-from_ancientgreek`` | from unicode to GF ancient Greek transliteration
| ``-from_arabic`` | from unicode to GF Arabic transliteration
| ``-from_arabic_unvocalized`` | from unicode to GF unvocalized Arabic transliteration
| ``-from_cp1251`` | decode from cp1251 (Cyrillic used in Bulgarian resource)
| ``-from_devanagari`` | from unicode to GF Devanagari transliteration
| ``-from_greek`` | from unicode to GF modern Greek transliteration
@@ -453,11 +469,14 @@ sequences; see example.
| ``-from_urdu`` | from unicode to GF Urdu transliteration
| ``-from_utf8`` | decode from utf8 (default)
| ``-lexcode`` | code-like lexer
| ``-lexgreek`` | lexer normalizing ancient Greek accentuation
| ``-lexgreek2`` | lexer normalizing ancient Greek accentuation for text with vowel length annotations
| ``-lexmixed`` | mixture of text and code, as in LaTeX (code between $...$, \(...)\, \[...\])
| ``-lextext`` | text-like lexer
| ``-to_amharic`` | from GF Amharic transliteration to unicode
| ``-to_ancientgreek`` | from GF ancient Greek transliteration to unicode
| ``-to_arabic`` | from GF Arabic transliteration to unicode
| ``-to_arabic_unvocalized`` | from GF unvocalized Arabic transliteration to unicode
| ``-to_cp1251`` | encode to cp1251 (Cyrillic used in Bulgarian resource)
| ``-to_devanagari`` | from GF Devanagari transliteration to unicode
| ``-to_greek`` | from GF modern Greek transliteration to unicode
@@ -473,6 +492,7 @@ sequences; see example.
| ``-to_utf8`` | encode to utf8 (default)
| ``-unchars`` | unlexer that puts no spaces between tokens
| ``-unlexcode`` | code-like unlexer
| ``-unlexgreek`` | unlexer de-normalizing ancient Greek accentuation
| ``-unlexmixed`` | mixture of text and code (code between $...$, \(...)\, \[...\])
| ``-unlextext`` | text-like unlexer
| ``-unwords`` | unlexer that puts a single space between tokens (default)
@@ -513,6 +533,7 @@ trees where a function node is a metavariable.
| ``-from_amharic`` | from unicode to GF Amharic transliteration
| ``-from_ancientgreek`` | from unicode to GF ancient Greek transliteration
| ``-from_arabic`` | from unicode to GF Arabic transliteration
| ``-from_arabic_unvocalized`` | from unicode to GF unvocalized Arabic transliteration
| ``-from_cp1251`` | decode from cp1251 (Cyrillic used in Bulgarian resource)
| ``-from_devanagari`` | from unicode to GF Devanagari transliteration
| ``-from_greek`` | from unicode to GF modern Greek transliteration
@@ -526,11 +547,14 @@ trees where a function node is a metavariable.
| ``-from_urdu`` | from unicode to GF Urdu transliteration
| ``-from_utf8`` | decode from utf8 (default)
| ``-lexcode`` | code-like lexer
| ``-lexgreek`` | lexer normalizing ancient Greek accentuation
| ``-lexgreek2`` | lexer normalizing ancient Greek accentuation for text with vowel length annotations
| ``-lexmixed`` | mixture of text and code, as in LaTeX (code between $...$, \(...)\, \[...\])
| ``-lextext`` | text-like lexer
| ``-to_amharic`` | from GF Amharic transliteration to unicode
| ``-to_ancientgreek`` | from GF ancient Greek transliteration to unicode
| ``-to_arabic`` | from GF Arabic transliteration to unicode
| ``-to_arabic_unvocalized`` | from GF unvocalized Arabic transliteration to unicode
| ``-to_cp1251`` | encode to cp1251 (Cyrillic used in Bulgarian resource)
| ``-to_devanagari`` | from GF Devanagari transliteration to unicode
| ``-to_greek`` | from GF modern Greek transliteration to unicode
@@ -546,6 +570,7 @@ trees where a function node is a metavariable.
| ``-to_utf8`` | encode to utf8 (default)
| ``-unchars`` | unlexer that puts no spaces between tokens
| ``-unlexcode`` | code-like unlexer
| ``-unlexgreek`` | unlexer de-normalizing ancient Greek accentuation
| ``-unlexmixed`` | mixture of text and code (code between $...$, \(...)\, \[...\])
| ``-unlextext`` | text-like unlexer
| ``-unwords`` | unlexer that puts a single space between tokens (default)
@@ -666,10 +691,9 @@ command (flag -printer):
fa finite automaton in graphviz format
gsl Nuance speech recognition format
haskell Haskell (abstract syntax)
java Java (abstract syntax)
js JavaScript (whole grammar)
jsgf JSGF speech recognition format
lambda_prolog LambdaProlog (abstract syntax)
lp_byte_code Bytecode for Teyjus (abstract syntax, experimental)
pgf_pretty human-readable pgf
prolog Prolog (whole grammar)
python Python (whole grammar)
@@ -753,6 +777,7 @@ To see transliteration tables, use command ut.
| ``-from_amharic`` | from unicode to GF Amharic transliteration
| ``-from_ancientgreek`` | from unicode to GF ancient Greek transliteration
| ``-from_arabic`` | from unicode to GF Arabic transliteration
| ``-from_arabic_unvocalized`` | from unicode to GF unvocalized Arabic transliteration
| ``-from_cp1251`` | decode from cp1251 (Cyrillic used in Bulgarian resource)
| ``-from_devanagari`` | from unicode to GF Devanagari transliteration
| ``-from_greek`` | from unicode to GF modern Greek transliteration
@@ -766,11 +791,14 @@ To see transliteration tables, use command ut.
| ``-from_urdu`` | from unicode to GF Urdu transliteration
| ``-from_utf8`` | decode from utf8 (default)
| ``-lexcode`` | code-like lexer
| ``-lexgreek`` | lexer normalizing ancient Greek accentuation
| ``-lexgreek2`` | lexer normalizing ancient Greek accentuation for text with vowel length annotations
| ``-lexmixed`` | mixture of text and code, as in LaTeX (code between $...$, \(...)\, \[...\])
| ``-lextext`` | text-like lexer
| ``-to_amharic`` | from GF Amharic transliteration to unicode
| ``-to_ancientgreek`` | from GF ancient Greek transliteration to unicode
| ``-to_arabic`` | from GF Arabic transliteration to unicode
| ``-to_arabic_unvocalized`` | from GF unvocalized Arabic transliteration to unicode
| ``-to_cp1251`` | encode to cp1251 (Cyrillic used in Bulgarian resource)
| ``-to_devanagari`` | from GF Devanagari transliteration to unicode
| ``-to_greek`` | from GF modern Greek transliteration to unicode
@@ -786,6 +814,7 @@ To see transliteration tables, use command ut.
| ``-to_utf8`` | encode to utf8 (default)
| ``-unchars`` | unlexer that puts no spaces between tokens
| ``-unlexcode`` | code-like unlexer
| ``-unlexgreek`` | unlexer de-normalizing ancient Greek accentuation
| ``-unlexmixed`` | mixture of text and code (code between $...$, \(...)\, \[...\])
| ``-unlextext`` | text-like unlexer
| ``-unwords`` | unlexer that puts a single space between tokens (default)
@@ -799,13 +828,14 @@ To see transliteration tables, use command ut.
- Examples:
| ``l (EAdd 3 4) | ps -code`` | linearize code-like output
| ``ps -lexer=code | p -cat=Exp`` | parse code-like input
| ``l (EAdd 3 4) | ps -unlexcode`` | linearize code-like output
| ``ps -lexcode | p -cat=Exp`` | parse code-like input
| ``gr -cat=QCl | l | ps -bind`` | linearization output from LangFin
| ``ps -to_devanagari "A-p"`` | show Devanagari in UTF8 terminal
| ``rf -file=Hin.gf | ps -env=quotes -to_devanagari`` | convert translit to UTF8
| ``rf -file=Ara.gf | ps -from_utf8 -env=quotes -from_arabic`` | convert UTF8 to transliteration
| ``ps -to=chinese.trans "abc"`` | apply transliteration defined in file chinese.trans
| ``ps -lexgreek "a)gavoi` a)'nvrwpoi' tines*"`` | normalize ancient greek accentuation
#NORMAL
@@ -828,7 +858,6 @@ are type checking and semantic computation.
- Options:
| ``-compute`` | compute by using semantic definitions (def)
| ``-paraphrase`` | paraphrase by using semantic definitions (def)
| ``-largest`` | sort trees from largest to smallest, in number of nodes
| ``-nub`` | remove duplicate trees
| ``-smallest`` | sort trees from smallest to largest, in number of nodes
@@ -838,12 +867,10 @@ are type checking and semantic computation.
- Flags:
| ``-number`` | take at most this many trees
| ``-transfer`` | syntactic transfer by applying function, recursively in subtrees
- Examples:
| ``pt -compute (plus one two)`` | compute value
| ``p "4 dogs love 5 cats" | pt -transfer=digits2numeral | l`` | four...five...
#NORMAL
@@ -990,8 +1017,6 @@ This command requires a source grammar to be in scope, imported with 'import -re
The operations include the parameter constructors that are in scope.
The optional TYPE filters according to the value type.
The grep STRINGs filter according to other substrings of the type signatures.
This command must be a line of its own, and thus cannot be a part
of a pipe.
- Syntax: ``so (-grep=STRING)* TYPE?``
- Options:
@@ -1002,6 +1027,12 @@ of a pipe.
| ``-grep`` | substring used for filtering (the command can have many of these)
- Examples:
| ``so Det`` | show all opers that create a Det
| ``so -grep=Prep`` | find opers relating to Prep
| ``so | wf -file=/tmp/opers`` | write the list of opers to a file
#NORMAL
@@ -1113,6 +1144,7 @@ This command must be a line of its own, and thus cannot be a part of a pipe.
| ``-amharic`` | Amharic
| ``-ancientgreek`` | ancient Greek
| ``-arabic`` | Arabic
| ``-arabic_unvocalized`` | unvocalized Arabic
| ``-devanagari`` | Devanagari
| ``-greek`` | modern Greek
| ``-hebrew`` | unvocalized Hebrew
@@ -1137,35 +1169,41 @@ This command must be a line of its own, and thus cannot be a part of a pipe.
#TINY
Prints a dependency tree in the .dot format (the graphviz format, default)
or LaTeX (flag -output=latex)
or the CoNLL/MaltParser format (flag -output=conll for training, malt_input
for unanalysed input).
By default, the last argument is the head of every abstract syntax
function; moreover, the head depends on the head of the function above.
The graph can be saved in a file by the wf command as usual.
If the -view flag is defined, the graph is saved in a temporary file
which is processed by graphviz and displayed by the program indicated
by the flag. The target format is png, unless overridden by the
flag -format.
which is processed by dot (graphviz) and displayed by the program indicated
by the view flag. The target format is png, unless overridden by the
flag -format. Results from multiple trees are combined to pdf with convert (ImageMagick).
See also 'vp -showdep' for another visualization of dependencies.
- Options:
| ``-v`` | show extra information
| ``-conll2latex`` | convert conll to latex
- Flags:
| ``-file`` | configuration file for labels per fun, format 'fun l1 ... label ... l2'
| ``-format`` | format of the visualization file (default "png")
| ``-output`` | output format of graph source (default "dot")
| ``-view`` | program to open the resulting file (default "open")
| ``-abslabels`` | abstract configuration file for labels, format per line 'fun label*'
| ``-cnclabels`` | concrete configuration file for labels, format per line 'fun {words|*} pos label head'
| ``-file`` | same as abslabels (abstract configuration file)
| ``-format`` | format of the visualization file using dot (default "png")
| ``-output`` | output format of graph source (latex, conll, dot (default but deprecated))
| ``-view`` | program to open the resulting graph file (default "open")
| ``-lang`` | the language of analysis
- Examples:
| ``gr | vd`` | generate a tree and show dependency tree in .dot
| ``gr | vd -view=open`` | generate a tree and display dependency tree on a Mac
| ``gr -number=1000 | vd -file=dep.labels -output=malt`` | generate training treebank
| ``gr -number=100 | vd -file=dep.labels -output=malt_input`` | generate test sentences
| ``gr | vd -view=open`` | generate a tree and display dependency tree on with Mac's 'open'
| ``gr | vd -view=open -output=latex`` | generate a tree and display latex dependency tree with Mac's 'open'
| ``gr -number=1000 | vd -abslabels=Lang.labels -cnclabels=LangSwe.labels -output=conll`` | generate a random treebank
| ``rf -file=ex.conll | vd -conll2latex | wf -file=ex.tex`` | convert conll file to latex
#NORMAL
@@ -1182,15 +1220,16 @@ flag -format.
Prints a parse tree in the .dot format (the graphviz format).
The graph can be saved in a file by the wf command as usual.
If the -view flag is defined, the graph is saved in a temporary file
which is processed by graphviz and displayed by the program indicated
by the flag. The target format is png, unless overridden by the
flag -format.
which is processed by dot (graphviz) and displayed by the program indicated
by the view flag. The target format is png, unless overridden by the
flag -format. Results from multiple trees are combined to pdf with convert (ImageMagick).
- Options:
| ``-showcat`` | show categories in the tree nodes (default)
| ``-nocat`` | don't show categories
| ``-showdep`` | show dependency labels
| ``-showfun`` | show function names in the tree nodes
| ``-nofun`` | don't show function names (default)
| ``-showleaves`` | show the leaves of the tree (default)
@@ -1198,6 +1237,8 @@ flag -format.
- Flags:
| ``-lang`` | the language to visualize
| ``-file`` | configuration file for dependency labels with -deps, format per line 'fun label*'
| ``-format`` | format of the visualization file (default "png")
| ``-view`` | program to open the resulting file (default "open")
| ``-nodefont`` | font for tree nodes (default: Times -- graphviz standard font)
@@ -1210,7 +1251,8 @@ flag -format.
- Examples:
| ``p "John walks" | vp`` | generate a tree and show parse tree as .dot script
| ``gr | vp -view="open"`` | generate a tree and display parse tree on a Mac
| ``gr | vp -view=open`` | generate a tree and display parse tree on a Mac
| ``p "she loves us" | vp -view=open -showdep -file=uddeps.labels -nocat`` | show a visual variant of a dependency tree
#NORMAL
@@ -1227,9 +1269,9 @@ flag -format.
Prints a set of trees in the .dot format (the graphviz format).
The graph can be saved in a file by the wf command as usual.
If the -view flag is defined, the graph is saved in a temporary file
which is processed by graphviz and displayed by the program indicated
by the flag. The target format is postscript, unless overridden by the
flag -format.
which is processed by dot (graphviz) and displayed by the command indicated
by the view flag. The target format is postscript, unless overridden by the
flag -format. Results from multiple trees are combined to pdf with convert (ImageMagick).
With option -mk, use for showing library style function names of form 'mkC'.

Binary file not shown.

View File

@@ -1,132 +0,0 @@
<!DOCTYPE html>
<html>
<head>
<title>GF People</title>
<meta charset="UTF-8">
<link rel=stylesheet href="../css/style.css">
<meta name = "viewport" content = "width = device-width">
</head>
<body>
<center>
<IMG SRC="Logos/gf0.png" alt="[GF]">
<h1>Grammatical Framework: Authors and Acknowledgements</h1>
</center>
The current developers and maintainers are
<a href="http://www.chalmers.se/cse/EN/organization/divisions/computing-science/people/angelov-krasimir">Krasimir Angelov</a>,
<a href="http://www.cse.chalmers.se/~hallgren/">Thomas Hallgren</a>,
and
<a href="http://www.cse.chalmers.se/~aarne/">Aarne Ranta</a>. Bug reports should be
posted via the
<a href="http://code.google.com/p/grammatical-framework/issues/list">GF bug tracker</a>.
<p>
Also the following people have contributed code to some of the versions:
<dl>
<dt>Grégoire Détrez (University of Gothenburg)
<dt>Ramona Enache (University of Gothenburg)
<dt>
<a href="http://www.cse.chalmers.se/alumni/bringert">Björn Bringert</a> (University of Gothenburg)
<dt>
Håkan Burden (University of Gothenburg)
<dt>
Hans-Joachim Daniels (Karlsruhe)
<dt>
<a href="http://www.cs.chalmers.se/~markus">Markus Forsberg</a> (Chalmers)
<dt>
<a href="http://www.cs.chalmers.se/~krijo">Kristofer Johannisson</a> (University of Gothenburg)
<dt>
<a href="http://www.cs.chalmers.se/~janna">Janna Khegai</a> (Chalmers)
<dt>
<a href="http://www.cse.chalmers.se/~peb">Peter Ljunglöf</a> (University of Gothenburg)
<dt>
Petri Mäenpää (Nokia)
</dl>
At least the following colleagues are thanked for suggestions,
bug reports, and other indirect contributions to the code. (Notice:
these are early contributors - the list has not been updated since 2004 or so).
<p>
<a href="http://www.di.unito.it/~stefano/">Stefano Berardi</a> (Torino),
Pascal Boldini (Paris),
<a href="http://www.dur.ac.uk/~dcs0pcc/">Paul Callaghan</a> (Durham),
Lauri Carlson (Helsinki),
<a href="http://www.cse.chalmers.se/~koen">Koen Claessen</a> (Chalmers),
<a href="http://www.cling.gu.se/~cooper">Robin Cooper</a> (Gothenburg),
<a href="http://www.cse.chalmers.se/~coquand">Thierry Coquand</a> (Chalmers),
<a
href="http://www.xrce.xerox.com/people/dymetman/dymetman.html">Marc
Dymetman</a> (XRCE),
Bertrand Grégoire (Tudor Institure, Luxembourg),
<a href="http://www.cse.chalmers.se/~reiner">Reiner Hähnle</a> (Chalmers),
<a href="http://pauillac.inria.fr/~huet/">Gérard Huet</a> (INRIA),
<a href="http://www.cse.chalmers.se/~patrikj">Patrik Jansson</a> (Chalmers),
Bernard Jaulin (Paris),
<a href="http://www.xrce.xerox.com/people/karttunen/karttunen.html">
Lauri Karttunen</a> (PARC),
Matti Kinnunen (Nokia),
<a
href="http://www.xrce.xerox.com/people/lux/">Veronika
Lux</a> (XRCE),
Per Martin-Löf (Stockholm),
<a href="http://www.cse.chalmers.se/~bengt">Bengt Nordström</a> (Chalmers),
<a
href="http://www.cis.uni-muenchen.de/studenten/stud_homepages/okrslar/reklame.html">
Martin Okrslar</a> (CIS),
Jianmin Pang (Durham),
<a
href="http://www.xrce.xerox.com/people/pogodalla/index.fr.html">Sylvain
Pogodalla</a> (XRCE),
<a href="http://www.inria.fr/Loic.Pottier">Loïc Pottier</a> (INRIA),
<a href="http://www2.parc.com/istl/members/zaenen/">Annie Zaenen</a> (PARC)
<p>
The GF logo was designed by Uula Ranta.
<p>
From 2001 to 2004, GF enjoyed funding from the
<a href="http://www.vinnova.se">Vinnova</a> foundation, within the
<a href="http://www.cse.chalmers.se/research/group/Language-technology/ILT.html">
Interactive Languge Technology</a> project.
</body>
</html>

63
doc/gf-people.md Normal file
View File

@@ -0,0 +1,63 @@
---
title: "Grammatical Framework: Authors and Acknowledgements"
---
## Current maintainers
The current maintainers of GF are
[Krasimir Angelov](http://www.chalmers.se/cse/EN/organization/divisions/computing-science/people/angelov-krasimir),
[Thomas Hallgren](http://www.cse.chalmers.se/~hallgren/),
[Aarne Ranta](http://www.cse.chalmers.se/~aarne/),
[John J. Camilleri](http://johnjcamilleri.com), and
[Inari Listenmaa](https://inariksit.github.io/).
This page is otherwise not up to date.
For detailed data about contributors to the code repositories since 2007, see
[here (gf-core)](https://github.com/GrammaticalFramework/gf-core/graphs/contributors)
and
[here (gf-rgl)](https://github.com/GrammaticalFramework/gf-rgl/graphs/contributors).
## Previous contributors
The following people have contributed code to some of the versions:
- Grégoire Détrez (University of Gothenburg)
- Ramona Enache (University of Gothenburg)
- [Björn Bringert](http://www.cse.chalmers.se/alumni/bringert) (University of Gothenburg)
- Håkan Burden (University of Gothenburg)
- Hans-Joachim Daniels (Karlsruhe)
- [Markus Forsberg](http://www.cs.chalmers.se/~markus) (Chalmers)
- [Kristofer Johannisson](http://www.cs.chalmers.se/~krijo) (University of Gothenburg)
- [Janna Khegai](http://www.cs.chalmers.se/~janna) (Chalmers)
- [Peter Ljunglöf](http://www.cse.chalmers.se/~peb) (University of Gothenburg)
- Petri Mäenpää (Nokia)
At least the following colleagues are thanked for suggestions, bug
reports, and other indirect contributions to the code.
- [Stefano Berardi](http://www.di.unito.it/~stefano/) (Torino)
- Pascal Boldini (Paris)
- [Paul Callaghan](http://www.dur.ac.uk/~dcs0pcc/) (Durham)
- Lauri Carlson (Helsinki)
- [Koen Claessen](http://www.cse.chalmers.se/~koen) (Chalmers)
- [Robin Cooper](http://www.cling.gu.se/~cooper) (Gothenburg)
- [Thierry Coquand](http://www.cse.chalmers.se/~coquand) (Chalmers)
- [Marc Dymetman](http://www.xrce.xerox.com/people/dymetman/dymetman.html) (XRCE)
- Bertrand Grégoire (Tudor Institute, Luxembourg)
- [Reiner Hähnle](http://www.cse.chalmers.se/~reiner) (Chalmers)
- [Gérard Huet](http://pauillac.inria.fr/~huet/) (INRIA)
- [Patrik Jansson](http://www.cse.chalmers.se/~patrikj) (Chalmers)
- Bernard Jaulin (Paris)
- [Lauri Karttunen](http://www.xrce.xerox.com/people/karttunen/karttunen.html) (PARC)
- Matti Kinnunen (Nokia)
- [Veronika Lux](http://www.xrce.xerox.com/people/lux/) (XRCE)
- Per Martin-Löf (Stockholm)
- [Bengt Nordström](http://www.cse.chalmers.se/~bengt) (Chalmers)
- [Martin Okrslar](http://www.cis.uni-muenchen.de/studenten/stud_homepages/okrslar/reklame.html) (CIS)
- Jianmin Pang (Durham)
- [Sylvain Pogodalla](http://www.xrce.xerox.com/people/pogodalla/index.fr.html) (XRCE)
- [Loïc Pottier](http://www.inria.fr/Loic.Pottier) (INRIA)
- [Annie Zaenen](http://www2.parc.com/istl/members/zaenen/) (PARC)
The GF logo was designed by Uula Ranta.

View File

@@ -1,158 +0,0 @@
<!DOCTYPE html>
<html>
<head>
<title>GF Quickstart</title>
<link rel=stylesheet href="../css/style.css">
<meta name = "viewport" content = "width = device-width">
</head>
<body>
<center>
<img src="Logos/gf0.png">
<p>
Aarne Ranta
<p>
October 2011 for GF 3.3
<p>
<h1>Grammatical Framework Quick Start</h1>
</center>
This Quick Start shows a few examples of how GF can be used.
We assume that you have downloaded and installed GF, so that
the command <tt>gf</tt> works for you. See download and install
instructions <a href="../download/index.html">here</a>.
<h2>Want to try without downloading?</h2>
<a href="../demos/phrasebook/">Using GF translation</a> with an existing grammar.
<p>
<a href="../demos/gfse/">Writing GF grammars</a> in the cloud, without installing GF.
<h2>Using GF for translation and generation</h2>
When you have downloaded and installed GF:
<ol>
<li> Copy the files
<a href="../examples/tutorial/food/Food.gf"><tt>Food.gf</tt></a>,
<a href="../examples/tutorial/food/FoodEng.gf"><tt>FoodEng.gf</tt></a>, and
<a href="../examples/tutorial/food/FoodIta.gf"><tt>FoodIta.gf</tt></a>.
Or go to <tt>GF/examples/tutorial/food/</tt>, if you have downloaded the
GF sources.
<li> Start GF with the shell command (without the prompt <tt>$</tt>)
<pre>
$ gf FoodIta.gf FoodEng.gf
</pre>
Alternatively, start GF with <tt>gf</tt> and give the GF command <tt>import FoodIta.gf FoodEng.gf</tt>.
<li> <b>Translation</b>. Try your first translation by giving the GF command
<pre>
parse "this cheese is very very Italian" | linearize
</pre>
Notice that the parser accept the tabulator for word completion.
<li> <b>Generation</b>. Random-generate sentences in two languages:
<pre>
generate_random | linearize
</pre>
<li> <b>Other commands</b>. Use the help command
<pre>
help
</pre>
<li> <b>More examples</b>. Go to <tt>GF/examples/phrasebook</tt> or some other
subdirectory of <tt>GF/examples/</tt>. Or try a resource grammar by, for instance,
<pre>
import alltenses/LangEng.gfo alltenses/LangGer.gfo
parse -lang=Eng "I love you" | linearize -treebank
</pre>
The resource grammars are found relative to the value of <tt>GF_LIB_PATH</tt>, which
you may have to set; see <a href="../download/index.html">here</a> for instructions.
</ol>
<h2>Grammar development</h2>
Add words to the <tt>Food</tt>
grammars and try the above commands again. For instance, add the following lines:
<pre>
Bread : Kind ; -- in Food.gf
Bread = {s = "bread"} ; -- in FoodEng.gf
Bread = {s = "pane"} ; -- in FoodIta.gf
</pre>
and start GF again with the same command. Now you can even translate
<i>this bread is very Italian</i>.
</ol>
To lear more on GF commands and
grammar development, go to the one of the tutorials:
<ul>
<li> <a href="tutorial/gf-tutorial.html">GF Tutorial</a>: older, more programmer-oriented
<li> <a href="gf-lrec-2010.pdf">GF Resource Tutorial</a>: newer, more linguist-oriented
</ul>
To learn about how GF is used for easily writing grammars for 16 languages, consult the
<ul>
<li> <a href="../lib/doc/synopsis.html">GF Resource Grammar Library</a>.
</ul>
<h2>Run-time grammars and web applications</h2>
GF has its own "machine language", PGF (Portable Grammar Format),
which is recommended for use in applications at run time. To produce a PGF file from
the two grammars above, do
<pre>
gf -make FoodIta.gf FoodEng.gf
wrote Food.pgf
</pre>
You can use this in Haskell and Java programs, and also on web services, such as
<ul>
<li> the
<a href="http://cloud.grammaticalframework.org/minibar/minibar.html">minibar</a>
fridge magnets
</ul>
The quickest way to provide a GF web service is to start GF with the <tt>-server</tt> option:
<pre>
$ gf -server
This is GF version 3.3
Built on linux/i386 with ghc-7.0, flags: interrupt server cclazy
Document root = /usr/local/share/gf-3.3/www
Starting HTTP server, open http://localhost:41296/ in your web browser.
</pre>
You can view it locally by pointing your
browser to the URL shown. You can add your own <tt>.pgf</tt> grammar to the service by
copying it over to the <tt>documentRoot</tt> directory. Just push "reload" in
your browser after each such update.
<p>
To build more customized web application, consult the
<a href="http://code.google.com/p/grammatical-framework/wiki/SideBar?tm=6">developer wiki</a>.
<h2>User group</h2>
You are welcome to join the <A HREF="http://groups.google.com/group/gf-dev">User Group</A>
to get help and discuss GF-related issues!
</body></html>

Binary file not shown.

View File

@@ -1,493 +0,0 @@
GF Quick Reference
Aarne Ranta
April 4, 2006
% NOTE: this is a txt2tags file.
% Create an html file from this file using:
% txt2tags -thtml gf-reference.t2t
%!style:../css/style.css
%!target:html
%!options: --toc
%!postproc(html): <TITLE> <meta name = "viewport" content = "width = device-width"><TITLE>
%!postproc(html): <H1> <H1><a href="../"><IMG src="../doc/Logos/gf0.png"></a>
This is a quick reference on GF grammars. It aims to
cover all forms of expression available when writing
grammars. It assumes basic knowledge of GF, which
can be acquired from the
[GF Tutorial http://www.grammaticalframework.org/doc/tutorial/gf-tutorial.html].
Help on GF commands is obtained on line by the
help command (``help``), and help on invoking
GF with (``gf -help``).
===A complete example===
This is a complete example of a GF grammar divided
into three modules in files. The grammar recognizes the
phrases //one pizza// and //two pizzas//.
File ``Order.gf``:
```
abstract Order = {
cat
Order ;
Item ;
fun
One, Two : Item -> Order ;
Pizza : Item ;
}
```
File ``OrderEng.gf`` (the top file):
```
--# -path=.:prelude
concrete OrderEng of Order =
open Res, Prelude in {
flags startcat=Order ;
lincat
Order = SS ;
Item = {s : Num => Str} ;
lin
One it = ss ("one" ++ it.s ! Sg) ;
Two it = ss ("two" ++ it.s ! Pl) ;
Pizza = regNoun "pizza" ;
}
```
File ``Res.gf``:
```
resource Res = open Prelude in {
param Num = Sg | Pl ;
oper regNoun : Str -> {s : Num => Str} =
\dog -> {s = table {
Sg => dog ;
_ => dog + "s"
}
} ;
}
```
To use this example, do
```
% gf -- in shell: start GF
> i OrderEng.gf -- in GF: import grammar
> p "one pizza" -- parse string
> l Two Pizza -- linearize tree
```
===Modules and files===
One module per file.
File named ``Foo.gf`` contains module named
``Foo``.
Each module has the structure
```
moduletypename =
Inherits ** -- optional
open Opens in -- optional
{ Judgements }
```
Inherits are names of modules of the same type.
Inheritance can be restricted:
```
Mo[f,g], -- inherit only f,g from Mo
Lo-[f,g] -- inheris all but f,g from Lo
```
Opens are possible in ``concrete`` and ``resource``.
They are names of modules of these two types, possibly
qualified:
```
(M = Mo), -- refer to f as M.f or Mo.f
(Lo = Lo) -- refer to f as Lo.f
```
Module types and judgements in them:
```
abstract A -- cat, fun, def, data
concrete C of A -- lincat, lin, lindef, printname
resource R -- param, oper
interface I -- like resource, but can have
oper f : T without definition
instance J of I -- like resource, defines opers
that I leaves undefined
incomplete -- functor: concrete that opens
concrete CI of A = one or more interfaces
open I in ...
concrete CJ of A = -- completion: concrete that
CI with instantiates a functor by
(I = J) instances of open interfaces
```
The forms
``param``, ``oper``
may appear in ``concrete`` as well, but are then
not inherited to extensions.
All modules can moreover have ``flags`` and comments.
Comments have the forms
```
-- till the end of line
{- any number of lines between -}
--# used for compiler pragmas
```
A ``concrete`` can be opened like a ``resource``.
It is translated as follows:
```
cat C ---> oper C : Type =
lincat C = T T ** {lock_C : {}}
fun f : G -> C ---> oper f : A* -> C* = \g ->
lin f = t t g ** {lock_C = <>}
```
An ``abstract`` can be opened like an ``interface``.
Any ``concrete`` of it then works as an ``instance``.
===Judgements===
```
cat C -- declare category C
cat C (x:A)(y:B x) -- dependent category C
cat C A B -- same as C (x : A)(y : B)
fun f : T -- declare function f of type T
def f = t -- define f as t
def f p q = t -- define f by pattern matching
data C = f | g -- set f,g as constructors of C
data f : A -> C -- same as
fun f : A -> C; data C=f
lincat C = T -- define lin.type of cat C
lin f = t -- define lin. of fun f
lin f x y = t -- same as lin f = \x y -> t
lindef C = \s -> t -- default lin. of cat C
printname fun f = s -- printname shown in menus
printname cat C = s -- printname shown in menus
printname f = s -- same as printname fun f = s
param P = C | D Q R -- define parameter type P
with constructors
C : P, D : Q -> R -> P
oper h : T = t -- define oper h of type T
oper h = t -- omit type, if inferrable
flags p=v -- set value of flag p
```
Judgements are terminated by semicolons (``;``).
Subsequent judgments of the same form may share the
keyword:
```
cat C ; D ; -- same as cat C ; cat D ;
```
Judgements can also share RHS:
```
fun f,g : A -- same as fun f : A ; g : A
```
===Types===
Abstract syntax (in ``fun``):
```
C -- basic type, if cat C
C a b -- basic type for dep. category
(x : A) -> B -- dep. functions from A to B
(_ : A) -> B -- nondep. functions from A to B
(p,q : A) -> B -- same as (p : A)-> (q : A) -> B
A -> B -- same as (_ : A) -> B
Int -- predefined integer type
Float -- predefined float type
String -- predefined string type
```
Concrete syntax (in ``lincat``):
```
Str -- token lists
P -- parameter type, if param P
P => B -- table type, if P param. type
{s : Str ; p : P}-- record type
{s,t : Str} -- same as {s : Str ; t : Str}
{a : A} **{b : B}-- record type extension, same as
{a : A ; b : B}
A * B * C -- tuple type, same as
{p1 : A ; p2 : B ; p3 : C}
Ints n -- type of n first integers
```
Resource (in ``oper``): all those of concrete, plus
```
Tok -- tokens (subtype of Str)
A -> B -- functions from A to B
Int -- integers
Strs -- list of prefixes (for pre)
PType -- parameter type
Type -- any type
```
As parameter types, one can use any finite type:
``P`` defined in ``param P``,
``Ints n``, and record types of parameter types.
===Expressions===
Syntax trees = full function applications
```
f a b -- : C if fun f : A -> B -> C
1977 -- : Int
3.14 -- : Float
"foo" -- : String
```
Higher-Order Abstract syntax (HOAS): functions as arguments:
```
F a (\x -> c) -- : C if a : A, c : C (x : B),
fun F : A -> (B -> C) -> C
```
Tokens and token lists
```
"hello" -- : Tok, singleton Str
"hello" ++ "world" -- : Str
["hello world"] -- : Str, same as "hello" ++ "world"
"hello" + "world" -- : Tok, computes to "helloworld"
[] -- : Str, empty list
```
Parameters
```
Sg -- atomic constructor
VPres Sg P2 -- applied constructor
{n = Sg ; p = P3} -- record of parameters
```
Tables
```
table { -- by full branches
Sg => "mouse" ;
Pl => "mice"
}
table { -- by pattern matching
Pl => "mice" ;
_ => "mouse" -- wildcard pattern
}
table {
n => regn n "cat" -- variable pattern
}
table Num {...} -- table given with arg. type
table ["ox"; "oxen"] -- table as course of values
\\_ => "fish" -- same as table {_ => "fish"}
\\p,q => t -- same as \\p => \\q => t
t ! p -- select p from table t
case e of {...} -- same as table {...} ! e
```
Records
```
{s = "Liz"; g = Fem} -- record in full form
{s,t = "et"} -- same as {s = "et";t= "et"}
{s = "Liz"} ** -- record extension: same as
{g = Fem} {s = "Liz" ; g = Fem}
<a,b,c> -- tuple, same as {p1=a;p2=b;p3=c}
```
Functions
```
\x -> t -- lambda abstract
\x,y -> t -- same as \x -> \y -> t
\x,_ -> t -- binding not in t
```
Local definitions
```
let x : A = d in t -- let definition
let x = d in t -- let defin, type inferred
let x=d ; y=e in t -- same as
let x=d in let y=e in t
let {...} in t -- same as let ... in t
t where {...} -- same as let ... in t
```
Free variation
```
variants {x ; y} -- both x and y possible
variants {} -- nothing possible
```
Prefix-dependent choices
```
pre {"a" ; "an" / v} -- "an" before v, "a" otherw.
strs {"a" ; "i" ;"o"}-- list of condition prefixes
```
Typed expression
```
<t:T> -- same as t, to help type inference
```
Accessing bound variables in ``lin``: use fields ``$1, $2, $3,...``.
Example:
```
fun F : (A : Set) -> (El A -> Prop) -> Prop ;
lin F A B = {s = ["for all"] ++ A.s ++ B.$1 ++ B.s}
```
===Pattern matching===
These patterns can be used in branches of ``table`` and
``case`` expressions. Patterns are matched in the order in
which they appear in the grammar.
```
C -- atomic param constructor
C p q -- param constr. applied to patterns
x -- variable, matches anything
_ -- wildcard, matches anything
"foo" -- string
56 -- integer
{s = p ; y = q} -- record, matches extensions too
<p,q> -- tuple, same as {p1=p ; p2=q}
p | q -- disjunction, binds to first match
x@p -- binds x to what p matches
- p -- negation
p + "s" -- sequence of two string patterns
p* -- repetition of a string pattern
```
===Sample library functions===
```
-- lib/prelude/Predef.gf
drop : Int -> Tok -> Tok -- drop prefix of length
take : Int -> Tok -> Tok -- take prefix of length
tk : Int -> Tok -> Tok -- drop suffix of length
dp : Int -> Tok -> Tok -- take suffix of length
occur : Tok -> Tok -> PBool -- test if substring
occurs : Tok -> Tok -> PBool -- test if any char occurs
show : (P:Type) -> P ->Tok -- param to string
read : (P:Type) -> Tok-> P -- string to param
toStr : (L:Type) -> L ->Str -- find "first" string
-- lib/prelude/Prelude.gf
param Bool = True | False
oper
SS : Type -- the type {s : Str}
ss : Str -> SS -- construct SS
cc2 : (_,_ : SS) -> SS -- concat SS's
optStr : Str -> Str -- string or empty
strOpt : Str -> Str -- empty or string
bothWays : Str -> Str -> Str -- X++Y or Y++X
init : Tok -> Tok -- all but last char
last : Tok -> Tok -- last char
prefixSS : Str -> SS -> SS
postfixSS : Str -> SS -> SS
infixSS : Str -> SS -> SS -> SS
if_then_else : (A : Type) -> Bool -> A -> A -> A
if_then_Str : Bool -> Str -> Str -> Str
```
===Flags===
Flags can appear, with growing priority,
- in files, judgement ``flags`` and without dash (``-``)
- as flags to ``gf`` when invoked, with dash
- as flags to various GF commands, with dash
Some common flags used in grammars:
```
startcat=cat use this category as default
lexer=literals int and string literals recognized
lexer=code like program code
lexer=text like text: spacing, capitals
lexer=textlit text, unknowns as string lits
unlexer=code like program code
unlexer=codelit code, remove string lit quotes
unlexer=text like text: punctuation, capitals
unlexer=textlit text, remove string lit quotes
unlexer=concat remove all spaces
unlexer=bind remove spaces around "&+"
optimize=all_subs best for almost any concrete
optimize=values good for lexicon concrete
optimize=all usually good for resource
optimize=noexpand for resource, if =all too big
```
For the full set of values for ``FLAG``,
use on-line ``h -FLAG``.
===File import search paths===
Colon-separated list of directories searched in the
given order:
```
--# -path=.:../abstract:../common:prelude
```
This can be (in order of increasing priority), as
first line in the file, as flag to ``gf``
when invoked, or as flag to the ``i`` command.
The prefix ``--#`` is used only in files.
GF attempts to satisfy an ``import`` command by searching for the
import filename in the above search paths, initially qualified
relative to the current working directory. If the file is not found in
that initial expansion, the search paths are re-qualified relative to
the directories given in the ``GF_LIB_PATH`` environment variable. If
``GF_LIB_PATH`` is not defined, its default value is
``/usr/local/share/gf-3.9/lib`` (assuming you have GF version 3.9).
If your GF resource grammar libraries are installed somewhere else,
you will want to set ``GF_LIB_PATH`` to point there instead. In a
pinch, you can point to the ``GF/lib/src/`` folder in your clone of
the GF source code repository.
Developers of resource grammars may find it useful to define multiple
directories, colon-separated, in ``GF_LIB_PATH``.
===Alternative grammar formats===
**Old GF** (before GF 2.0):
all judgements in any kinds of modules,
division into files uses ``include``s.
A file ``Foo.gf`` is recognized as the old format
if it lacks a module header.
**Context-free** (file ``foo.cf``). The form of rules is e.g.
```
Fun. S ::= NP "is" AP ;
```
If ``Fun`` is omitted, it is generated automatically.
Rules must be one per line. The RHS can be empty.
**Extended BNF** (file ``foo.ebnf``). The form of rules is e.g.
```
S ::= (NP+ ("is" | "was") AP | V NP*) ;
```
where the RHS is a regular expression of categories
and quoted tokens: ``"foo", CAT, T U, T|U, T*, T+, T?``, or empty.
Rule labels are generated automatically.
**Probabilistic grammars** (not a separate format).
You can set the probability of a function ``f`` (in its value category) by
```
--# prob f 0.009
```
These are put into a file given to GF using the ``probs=File`` flag
on command line. This file can be the grammar file itself.
**Example-based grammars** (file ``foo.gfe``). Expressions of the form
```
in Cat "example string"
```
are preprocessed by using a parser given by the flag
```
--# -resource=File
```
and the result is written to ``foo.gf``.
===References===
[GF Homepage http://www.grammaticalframework.org/]
A. Ranta, Grammatical Framework: A Type-Theoretical Grammar Formalism.
//The Journal of Functional Programming//, vol. 14:2. 2004, pp. 145-189.

File diff suppressed because it is too large Load Diff

2770
doc/gf-refman.md Normal file

File diff suppressed because it is too large Load Diff

View File

@@ -1,11 +1,8 @@
The GF Software System
%!style:../css/style.css
%!options(html): --toc
%!options(html): --toc-level=4
%!postproc(html): <TITLE> <meta name = "viewport" content = "width = device-width"><TITLE>
%!postproc(html): <H1> <H1><a href="../"><IMG src="../doc/Logos/gf0.png"></a>
%!postproc(html): "#VSPACE" "<hr>"
%!postproc(html): "#NORMAL" ""
%!postproc(html): "#TINY" ""
@@ -13,7 +10,7 @@ The GF Software System
The GF software system implements the GF programming language. Its
components are
- the //compiler//,
- the //compiler//,
translating ``.gf`` source files to ``.gfo`` object files, to
``.pgf`` run-time grammars, and to various other formats
- the //run-time system//,
@@ -43,7 +40,7 @@ The shell maintains a //state//, to which belong
Unless file arguments are provided to the ``gf`` command, the shell starts in an
empty state, with no grammars and no history.
empty state, with no grammars and no history.
In the shell, a set of commands
is available. Some of these commands may change the grammars in the state. The general
@@ -59,7 +56,7 @@ syntax of commands is given by the following BNF grammar:
ARGUMENT ::= QUOTED_STRING | TREE
VALUE ::= IDENT | QUOTED_STRING
```
A command pipe is a sequence of commands interpreted in such a way
A command pipe is a sequence of commands interpreted in such a way
that the output of each command
is send as input to the next. The option ``-tr`` causes GF to show a trace,
i.e. the intermediate result of the command to which it is attached.
@@ -69,7 +66,7 @@ executed one by one, in the order of appearance.
===GF shell commands===
The full set of GF shell commands is listed below with explanations.
The full set of GF shell commands is listed below with explanations.
This list can also be obtained in the GF shell by the command ``help -full``.
%!include: gf-help-full.txt
@@ -77,14 +74,14 @@ This list can also be obtained in the GF shell by the command ``help -full``.
==The GF batch compiler==
With the option ``-batch``, GF can be invoked in batch mode, i.e.
without opening the shell, to compile files from ``.gf`` to ``.gfo``.
The ``-s`` option ("silent") eliminates all messages except errors.
without opening the shell, to compile files from ``.gf`` to ``.gfo``.
The ``-s`` option ("silent") eliminates all messages except errors.
```
$ gf -batch -s LangIta.gf
```
With the option ``-make``, and as a set of
top-level grammar files (with the same abstract syntax) as arguments,
GF produces a ``.pgf`` file. The flag ``-optimize-pgf`` minimizes
GF produces a ``.pgf`` file. The flag ``-optimize-pgf`` minimizes
the size of the ``.pgf`` file, and is recommended for grammars to be shipped.
```
$ gf -make -optimize-pgf LangIta.gf LangEng.gf LangGer.gf
@@ -107,5 +104,3 @@ To run GF from a //script//, redirection of standard input can be used:
```
The file ``script.gfs`` should then contain a sequence of GF commands, one per line.
Unrecognized command lines are skipped without terminating GF.

View File

@@ -1,69 +0,0 @@
<!DOCTYPE html>
<html>
<head>
<title>GF Documentation</title>
<link rel=stylesheet href="../css/style.css">
</head>
<body>
<div class=center>
<a href="../"><img src="Logos/gf0.png"></a>
<h1>Grammatical Framework Documents</h1>
</div>
<b>Top-5 documents</b>:
<a href="gf-quickstart.html">Quick start instruction</a>.
<a href="tutorial/gf-tutorial.html">Old Tutorial</a>, application-oriented.
<a href="gf-lrec-2010.pdf">New Tutorial</a>, linguistics-oriented.
<a href="gf-refman.html">ReferenceManual</a>.
<a href="../lib/resource/doc/synopsis.html">LibrarySynopsis</a>.
<h2>Language and system documentation</h2>
<ul>
<li>
<a href="gf-reference.html">GF Quick Reference</a>. Also available in
<a href="gf-reference.pdf">pdf</a>. Covers all features of GF language
in a summary format.
<li>
<a href="gf-refman.html">GF Reference Manual</a>. A full-scale reference
manual of the GF language.
<li>
<a href="gf-shell-reference.html">GF Shell Reference</a>.
Describes the commands available in the interactive GF shell. Also
summarizes how to run GF as a batch compiler.
<li>
<a href="gf-editor-modes.html">Editor modes for GF</a>.
Editor modes for GF provides syntax highligting, automatic indentation and
other features that makes editing GF grammar files easier.
</ul>
<h2>Publications</h2>
<a href="gf-bibliography.html">
Bibliography</a>: more publications on GF, as well as background literature.
</body></html>

13
doc/index.md Normal file
View File

@@ -0,0 +1,13 @@
---
title: Grammatical Framework Documentation
---
Perhaps you're looking for one of the following:
- [Tutorial](tutorial/gf-tutorial.html). This is a hands-on introduction to grammar writing in GF.
- [Reference Manual](gf-refman.html). A full-scale reference manual of the GF language.
- [RGL Tutorial](../lib/doc/rgl-tutorial/index.html)
- [RGL Synopsis](../lib/doc/synopsis/index.html). Documentation of the Resource Grammar Library, including the syntax API and lexical paradigms for each language.
- [Shell Reference](gf-shell-reference.html). Describes the commands available in the interactive GF shell.
Also summarizes how to run GF as a batch compiler.
- [Developers Guide](gf-developers/html). Detailed information about building and developing GF.

View File

@@ -1,29 +1,26 @@
<html>
<!DOCTYPE html>
<html xmlns="http://www.w3.org/1999/xhtml" lang="en" xml:lang="en">
<head>
<title>C Runtime API</title>
<meta charset="utf-8" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<link rel="stylesheet" href="https://stackpath.bootstrapcdn.com/bootstrap/4.1.3/css/bootstrap.min.css" integrity="sha384-MCw98/SFnGE8fJT3GXwEOngsV7Zt27NXFoaoApmYm81iuXoPkFOJwJ8ERdknLPMO" crossorigin="anonymous">
<style>
body { background: #eee; padding-top: 200px; }
pre.python {background-color:#ffc; display: none}
pre.haskell {background-color:#ffc; display: block}
pre.java {background-color:#ffc; display: none}
pre.csharp {background-color:#ffc; display: none}
pre {
background-color:#eee;
margin-top: 1em;
padding: 0.5em 1em;
}
pre.python {display: none}
pre.haskell {display: block}
pre.java {display: none}
pre.csharp {display: none}
span.python {display: none}
span.haskell {display: inline}
span.java {display: none}
span.csharp {display: none}
.header {
position: fixed;
top: 0;
left: 0;
background: #ddd;
width: 100%;
padding: 5pt;
border-bottom: solid #bbb 2pt;
}
</style>
<script lang="javascript">
function change_language(href) {
var name = href.split("#")[1];
@@ -50,14 +47,28 @@
</script>
</head>
<body onload="change_language(window.location.href); window.addEventListener('hashchange', function(e){change_language(window.location.href);});">
<span class="header">
<h1>Using the <span class="python">Python</span> <span class="haskell">Haskell</span> <span class="java">Java</span> <span class="csharp">C#</span> binding to the C runtime</h1>
Choose a language: <a href="#haskell">Haskell</a> <a href="#python">Python</a> <a href="#java">Java</a> <a href="#csharp">C#</a>
</span>
<div class="container-fluid" style="max-width: 1200px">
<div class="header sticky-top border-bottom py-3 bg-white">
<a href=".." title="Home">
<img src="../doc/Logos/gf1.svg" height="120px" class="float-md-right ml-3 mb-3 bg-white" alt="GF Logo">
</a>
<h1>
Using the
<span class="python">Python</span>
<span class="haskell">Haskell</span>
<span class="java">Java</span>
<span class="csharp">C#</span>
binding to the C runtime
</h1>
<h4 class="text-muted">Krasimir Angelov, July 2015 - August 2017</h4>
Choose a language:
<a href="#haskell" class="mx-1">Haskell</a>
<a href="#python" class="mx-1">Python</a>
<a href="#java" class="mx-1">Java</a>
<a href="#csharp" class="mx-1">C#</a>
</div>
<main class="py-4">
<h4>Krasimir Angelov, July 2015 - August 2017</h4>
<h2>Loading the Grammar</h2>
Before you use the <span class="python">Python</span> binding you need to import the <span class="haskell">PGF2 module</span><span class="python">pgf module</span><span class="java">pgf package</span><span class="csharp">PGFSharp package</span>:
@@ -127,7 +138,7 @@ Concr eng = gr.Languages["AppEng"];
<h2>Parsing</h2>
All language specific services are available as
All language specific services are available as
<span class="python">methods of the class <tt>pgf.Concr</tt></span><span class="haskell">functions that take as an argument an object of type <tt>Concr</tt></span><span class="java">methods of the class <tt>Concr</tt></span><span class="csharp">methods of the class <tt>Concr</tt></span>.
For example to invoke the parser, you can call:
<pre class="python">
@@ -220,10 +231,10 @@ Console.WriteLine(ep.Item1);
PhrUtt NoPConj (UttS (UseCl (TTAnt TPres ASimul) PPos (PredVP (DetNP (DetQuant this_Quant NumSg)) (UseComp (CompNP (DetCN (DetQuant IndefArt NumSg) (AdjCN (PositA small_A) (UseN theatre_N)))))))) NoVoc
</pre>
<p>Note that depending on the grammar it is absolutely possible that for
a single sentence you might get infinitely many trees.
<p>Note that depending on the grammar it is absolutely possible that for
a single sentence you might get infinitely many trees.
In other cases the number of trees might be finite but still enormous.
The parser is specifically designed to be lazy, which means that
The parser is specifically designed to be lazy, which means that
each tree is returned as soon as it is found before exhausting
the full search space. For grammars with a patological number of
trees it is advisable to pick only the top <tt>N</tt> trees
@@ -246,16 +257,16 @@ parsing with a different start category can be done as follows:</p>
</pre>
</span>
<span class="haskell">
There is also the function <tt>parseWithHeuristics</tt> which
takes two more paramaters which let you to have a better control
There is also the function <tt>parseWithHeuristics</tt> which
takes two more paramaters which let you to have a better control
over the parser's behaviour:
<pre class="haskell">
Prelude PGF2> let res = parseWithHeuristics eng (startCat gr) heuristic_factor callbacks
</pre>
</span>
<span class="java">
There is also the method <tt>parseWithHeuristics</tt> which
takes two more paramaters which let you to have a better control
There is also the method <tt>parseWithHeuristics</tt> which
takes two more paramaters which let you to have a better control
over the parser's behaviour:
<pre class="java">
Iterable&lt;ExprProb&gt; iterable = eng.parseWithHeuristics(gr.startCat(), heuristic_factor, callbacks);
@@ -281,7 +292,7 @@ to factor 0.0. When we increase the factor then parsing becomes faster
but at the same time the sorting becomes imprecise. The worst
factor is 1.0. In any case the parser always returns the same set of
trees but in different order. Our experience is that even a factor
of about 0.6-0.8 with the translation grammar still orders
of about 0.6-0.8 with the translation grammar still orders
the most probable tree on top of the list but further down the list,
the trees become shuffled.
</p>
@@ -457,7 +468,7 @@ the object has the following public final variables:
</span>
</p>
The linearization works even if there are functions in the tree
The linearization works even if there are functions in the tree
that doesn't have linearization definitions. In that case you
will just see the name of the function in the generated string.
It is sometimes helpful to be able to see whether a function
@@ -483,7 +494,7 @@ true
<p>
An already constructed tree can be analyzed and transformed
in the host application. For example you can deconstruct
in the host application. For example you can deconstruct
a tree into a function name and a list of arguments:
<pre class="python">
>>> e.unpack()
@@ -523,8 +534,8 @@ literal. For example the result from:
<span class="haskell">
The result from <tt>unApp</tt> is <tt>Just</tt> if the expression
is an application and <tt>Nothing</tt> in all other cases.
Similarly, if the tree is a literal string then the return value
from <tt>unStr</tt> will be <tt>Just</tt> with the actual literal.
Similarly, if the tree is a literal string then the return value
from <tt>unStr</tt> will be <tt>Just</tt> with the actual literal.
For example the result from:
</span>
<pre class="haskell">
@@ -534,8 +545,8 @@ Prelude PGF2> readExpr "\"literal\"" >>= unStr
<span class="java">
The result from <tt>unApp</tt> is not <tt>null</tt> if the expression
is an application, and <tt>null</tt> in all other cases.
Similarly, if the tree is a literal string then the return value
from <tt>unStr</tt> will not be <tt>null</tt> with the actual literal.
Similarly, if the tree is a literal string then the return value
from <tt>unStr</tt> will not be <tt>null</tt> with the actual literal.
For example the output from:
</span>
<pre class="java">
@@ -545,15 +556,15 @@ System.out.println(elit.unStr());
<span class="csharp">
The result from <tt>UnApp</tt> is not <tt>null</tt> if the expression
is an application, and <tt>null</tt> in all other cases.
Similarly, if the tree is a literal string then the return value
from <tt>UnStr</tt> will not be <tt>null</tt> with the actual literal.
Similarly, if the tree is a literal string then the return value
from <tt>UnStr</tt> will not be <tt>null</tt> with the actual literal.
For example the output from:
</span>
<pre class="csharp">
Expr elit = Expr.ReadExpr("\"literal\"");
Console.WriteLine(elit.UnStr());
</pre>
is just the string "literal".
is just the string "literal".
<span class="python">Situations like this can be detected
in Python by checking the type of the result from <tt>unpack</tt>.
It is also possible to get an integer or a floating point number
@@ -569,7 +580,7 @@ There are also the methods <tt>UnAbs</tt>, <tt>UnInt</tt>, <tt>UnFloat</tt> and
</span>
</p>
Constructing new trees is also easy. You can either use
Constructing new trees is also easy. You can either use
<tt>readExpr</tt> to read trees from strings, or you can
construct new trees from existing pieces. This is possible by
<span class="python">
@@ -612,7 +623,7 @@ Console.WriteLine(e2);
<p>If the host application needs to do a lot of expression manipulations,
then it is helpful to use a higher-level API to the grammar,
also known as "embedded grammars" in GF. The advantage is that
you can construct and analyze expressions in a more compact way.</p>
you can construct and analyze expressions in a more compact way.</p>
<span class="python">
<p>In Python you first have to <tt>embed</tt> the grammar by calling:
@@ -721,7 +732,7 @@ call the method <tt>default</tt>. The following is an example:
def on_DetCN(self,quant,cn):
print("Found DetCN")
cn.visit(self)
def on_AdjCN(self,adj,cn):
print("Found AdjCN")
cn.visit(self)
@@ -1007,7 +1018,7 @@ Traceback (most recent call last):
pgf.PGFError: The concrete syntax is not loaded
</pre>
Before using the concrete syntax, you need to explicitly load it:
Before using the concrete syntax, you need to explicitly load it:
<pre class="python">
>>> eng.load("AppEng.pgf_c")
>>> print(eng.lookupMorpho("letter"))
@@ -1060,7 +1071,7 @@ Traceback (most recent call last):
pgf.PGFError: The concrete syntax is not loaded
</pre>
Before using the concrete syntax, you need to explicitly load it:
Before using the concrete syntax, you need to explicitly load it:
<pre class="java">
eng.load("AppEng.pgf_c")
for (MorphoAnalysis an : eng.lookupMorpho("letter")) {
@@ -1289,6 +1300,7 @@ graph {
}
</pre>
</main>
</div>
</body>
</html>

View File

@@ -8,7 +8,7 @@ December 2010 for GF 3.2
% txt2tags --toc -ttex gf-tutorial.txt
%!target:html
%!encoding: iso-8859-1
%!encoding: utf-8
%!options: --toc
%!postproc(tex) : "\\subsection\*" "\\newslide"
@@ -618,32 +618,32 @@ and **semantic definitions**.
#NEW
==Slides==
You can chop this tutorial into a set of slides by the command
```
htmls gf-tutorial.html
```
where the program ``htmls`` is distributed with GF (see below), in
[``GF/src/tools/Htmls.hs`` http://grammaticalframework.org/src/tools/Htmls.hs]
The slides will appear as a set of files beginning with ``01-gf-tutorial.htmls``.
Internal links will not work in the slide format, except for those in the
upper left corner of each slide, and the links behind the "Contents" link.
% #NEW
%
% ==Slides==
%
% You can chop this tutorial into a set of slides by the command
% ```
% htmls gf-tutorial.html
% ```
% where the program ``htmls`` is distributed with GF (see below), in
%
% [``GF/src/tools/Htmls.hs`` http://grammaticalframework.org/src/tools/Htmls.hs]
%
% The slides will appear as a set of files beginning with ``01-gf-tutorial.htmls``.
%
% Internal links will not work in the slide format, except for those in the
% upper left corner of each slide, and the links behind the "Contents" link.
#NEW
#Lchaptwo
=Lesson 1: Getting Started with GF=
#Lchaptwo
Goals:
- install and run GF
- write the first GF grammar: a "Hello World" grammar in three languages
@@ -836,8 +836,8 @@ Finnish and an Italian concrete syntaxes:
lin
Hello recip = {s = "terve" ++ recip.s} ;
World = {s = "maailma"} ;
Mum = {s = "äiti"} ;
Friends = {s = "ystävät"} ;
Mum = {s = "äiti"} ;
Friends = {s = "ystävät"} ;
}
concrete HelloIta of Hello = {
@@ -925,7 +925,7 @@ Default of the language flag (``-lang``): the last-imported concrete syntax.
**Multilingual generation**:
```
> parse -lang=HelloEng "hello friends" | linearize
terve ystävät
terve ystävät
ciao amici
hello friends
```
@@ -1037,9 +1037,10 @@ Application programs, using techniques from #Rchapeight:
#NEW
#Lchapthree
=Lesson 2: Designing a grammar for complex phrases=
#Lchapthree
Goals:
- build a larger grammar: phrases about food in English and Italian
@@ -1335,7 +1336,7 @@ Just (?) replace English words with their dictionary equivalents:
Phrase, Item, Kind, Quality = {s : Str} ;
lin
Is item quality = {s = item.s ++ "č" ++ quality.s} ;
Is item quality = {s = item.s ++ "è" ++ quality.s} ;
This kind = {s = "questo" ++ kind.s} ;
That kind = {s = "quel" ++ kind.s} ;
QKind quality kind = {s = kind.s ++ quality.s} ;
@@ -1446,11 +1447,11 @@ linearizations in different languages:
> gr -number=2 | l -treebank
Is (That Cheese) (Very Boring)
quel formaggio č molto noioso
quel formaggio è molto noioso
that cheese is very boring
Is (That Cheese) Fresh
quel formaggio č fresco
quel formaggio è fresco
that cheese is fresh
```
@@ -1472,14 +1473,14 @@ answer given in another language.
You can interrupt the quiz by entering a line consisting of a dot ('.').
this fish is warm
questo pesce č caldo
questo pesce è caldo
> Yes.
Score 1/1
this cheese is Italian
questo formaggio č noioso
> No, not questo formaggio č noioso, but
questo formaggio č italiano
questo formaggio è noioso
> No, not questo formaggio è noioso, but
questo formaggio è italiano
Score 1/2
this fish is expensive
@@ -1756,7 +1757,7 @@ Simultaneous extension and opening:
lincat
Question = SS ;
lin
QIs item quality = ss (item.s ++ "č" ++ quality.s) ;
QIs item quality = ss (item.s ++ "è" ++ quality.s) ;
Pizza = ss "pizza" ;
}
```
@@ -1797,9 +1798,10 @@ where
#NEW
#Lchapfour
=Lesson 3: Grammars with parameters=
#Lchapfour
Goals:
- implement sophisticated linguistic structures:
@@ -2364,10 +2366,10 @@ in English, with special care taken of variations with the suffix
+ Implement the German **Umlaut** operation on word stems.
The operation changes the vowel of the stressed stem syllable as follows:
//a// to //ä//, //au// to //äu//, //o// to //ö//, and //u// to //ü//. You
//a// to //ä//, //au// to //äu//, //o// to //ö//, and //u// to //ü//. You
can assume that the operation only takes syllables as arguments. Test the
operation to see whether it correctly changes //Arzt// to //Ärzt//,
//Baum// to //Bäum//, //Topf// to //Töpf//, and //Kuh// to //Küh//.
operation to see whether it correctly changes //Arzt// to //Ärzt//,
//Baum// to //Bäum//, //Topf// to //Töpf//, and //Kuh// to //Küh//.
@@ -2480,10 +2482,10 @@ The command ``morpho_quiz = mq`` generates inflection exercises.
Welcome to GF Morphology Quiz.
...
réapparaître : VFin VCondit Pl P2
réapparaitriez
> No, not réapparaitriez, but
réapparaîtriez
réapparaître : VFin VCondit Pl P2
réapparaitriez
> No, not réapparaitriez, but
réapparaîtriez
Score 0/1
```
To create a list for later use, use the command ``morpho_list = ml``
@@ -2563,7 +2565,7 @@ We need only number variation for the copula.
```
copula : Number -> Str =
\n -> case n of {
Sg => "č" ;
Sg => "è" ;
Pl => "sono"
} ;
```
@@ -2772,9 +2774,10 @@ Thus
#NEW
#Lchapfive
=Lesson 4: Using the resource grammar library=
#Lchapfive
Goals:
- navigate in the GF resource grammar library and use it in applications
@@ -3305,13 +3308,13 @@ we can write a **functor instantiation**,
oper
wine_N = mkN "Wein" ;
pizza_N = mkN "Pizza" "Pizzen" feminine ;
cheese_N = mkN "Käse" "Käsen" masculine ;
cheese_N = mkN "Käse" "Käsen" masculine ;
fish_N = mkN "Fisch" ;
fresh_A = mkA "frisch" ;
warm_A = mkA "warm" "wärmer" "wärmste" ;
warm_A = mkA "warm" "wärmer" "wärmste" ;
italian_A = mkA "italienisch" ;
expensive_A = mkA "teuer" ;
delicious_A = mkA "köstlich" ;
delicious_A = mkA "köstlich" ;
boring_A = mkA "langweilig" ;
}
```
@@ -3362,11 +3365,11 @@ Lexicon instance
cheese_N = mkN "juusto" ;
fish_N = mkN "kala" ;
fresh_A = mkA "tuore" ;
warm_A = mkA "lämmin" ;
warm_A = mkA "lämmin" ;
italian_A = mkA "italialainen" ;
expensive_A = mkA "kallis" ;
delicious_A = mkA "herkullinen" ;
boring_A = mkA "tylsä" ;
boring_A = mkA "tylsä" ;
}
```
Functor instantiation
@@ -3614,9 +3617,10 @@ tenses and moods, e.g. the Romance languages.
#NEW
#Lchapsix
=Lesson 5: Refining semantics in abstract syntax=
#Lchapsix
Goals:
- include semantic conditions in grammars, by using
@@ -3626,7 +3630,7 @@ Goals:
- semantic definitions
These concepts are inherited from **type theory** (more precisely:
constructive type theory, or Martin-Löf type theory).
constructive type theory, or Martin-Löf type theory).
Type theory is the basis **logical frameworks**.
@@ -4177,11 +4181,11 @@ Type checking can be invoked with ``put_term -transform=solve``.
#NEW
#Lchapseven
==Lesson 6: Grammars of formal languages==
#Lchapseven
Goals:
- write grammars for formal languages (mathematical notation, programming languages)
- interface between formal and natural langauges
@@ -4516,9 +4520,10 @@ point literals as arguments.
#NEW
#Lchapeight
=Lesson 7: Embedded grammars=
#Lchapeight
Goals:
- use grammars as parts of programs written in Haskell and JavaScript
@@ -4639,7 +4644,7 @@ output. Therefore it can be a part of a pipe and read and write files.
The simplest way to translate is to ``echo`` input to the program:
```
% echo "this wine is delicious" | ./trans Food.pgf
questo vino č delizioso
questo vino è delizioso
```
The result is given in all languages except the input language.
@@ -4958,12 +4963,12 @@ syntax name. This file contains the multilingual grammar as a JavaScript object.
===Using the JavaScript grammar===
To perform parsing and linearization, the run-time library
``gflib.js`` is used. It is included in ``GF/lib/javascript/``, together with
``gflib.js`` is used. It is included in ``/src/runtime/javascript/``, together with
some other JavaScript and HTML files; these files can be used
as templates for building applications.
An example of usage is
[``translator.html`` http://grammaticalframework.org:41296],
[``translator.html`` ../../src/runtime/javascript/translator.html],
which is in fact initialized with
a pointer to the Food grammar, so that it provides translation between the English
and Italian grammars:

View File

@@ -1,13 +0,0 @@
#!/bin/sh
FILES="darcs.txt transfer-reference.txt transfer-tutorial.txt \
transfer.txt"
for f in $FILES; do
h=`basename "$f" ".txt"`.html
if [ "$f" -nt "$h" ]; then
txt2tags $f
else
echo "$h is newer than $f, skipping"
fi
done

View File

@@ -1,10 +1,6 @@
GF character encoding changes
Thomas Hallgren
%%mtime(%F)
%!style:../css/style.css
%!postproc(html): <TITLE> <meta charset="UTF-8"><meta name = "viewport" content = "width = device-width"> <TITLE>
%!postproc(html): <H1> <H1><a href="../"><IMG src="../doc/Logos/gf0.png"></a>
2013-12-18
==Changes to character encodings in GF grammar files ==

View File

@@ -16,7 +16,7 @@ GF 3.1.6 released 23 April 2010.
- Windows (zipped executable):
[``gf-3.1.6-bin-i486-windows.zip`` gf-3.1.6-bin-i486-windows.zip]
(1.6 MB)
- Ubuntu Linux (gzipped executable):
- Ubuntu Linux (gzipped executable):
[``gf-3.1.6-bin-i486-linux.gz`` gf-3.1.6-bin-i486-linux.gz]
(1.7 MB)
- compiled library package:
@@ -25,7 +25,7 @@ GF 3.1.6 released 23 April 2010.
- full source package (GF system, libraries, examples, documentation):
[``gf-3.1.6-src.tar.gz`` gf-3.1.6-src.tar.gz]
(11 MB)
GF is also on [Hackage http://hackage.haskell.org/package/gf]
@@ -40,7 +40,7 @@ What's new? See the [release notes release-3.1.6.html].
==Installation instructions==
The Windows package is installed by just unpacking it anywhere.
The Windows package is installed by just unpacking it anywhere.
It finds the libraries relative to the ``.exe`` file.
To install a binary package for MacOS X or Linux: uncompress the executable and

View File

@@ -1,11 +1,6 @@
Grammatical Framework Download and Installation
%!style:../css/style.css
%!postproc(html): <TD><B> <TH>
%!postproc(html): </B></TD> </TH>
%!postproc(html): <H1> <H1><a href="../"><IMG src="../doc/Logos/gf0.png"></a>
**GF 3.2.9** source-only snapshot was released on 12 September 2011.
What's new? Faster grammar compilation!
@@ -77,9 +72,3 @@ The above notes for installing from source apply also in this case.
- [GF 3.2 index-3.2.html] (December 2011).
- [GF 3.1.6 index-3.1.6.html] (April 2010).
- [GF 3.1 old-index.html] (December 2009).
--------------------
[www.grammaticalframework.org http://www.grammaticalframework.org]

View File

@@ -1,11 +1,6 @@
Grammatical Framework Download and Installation
%!style:../css/style.css
%!postproc(html): <TD><B> <TH>
%!postproc(html): </B></TD> </TH>
%!postproc(html): <H1> <H1><a href="../"><IMG src="../doc/Logos/gf0.png"></a>
**GF 3.2** was released on 23 December 2010.
What's new? See the [Release notes release-3.2.html].
@@ -27,7 +22,7 @@ More packages might be added later.
===Notes===
The Windows package is installed by just unpacking it anywhere.
The Windows package is installed by just unpacking it anywhere.
It finds the libraries relative to the ``.exe`` file.
The ``.deb`` packages work on Ubuntu 10.04 and 10.10.
@@ -105,8 +100,3 @@ Subsequently:
```
The above notes for installing from source apply also in this case.
--------------------
[www.grammaticalframework.org http://www.grammaticalframework.org]

View File

@@ -1,12 +1,6 @@
Grammatical Framework Download and Installation
%!style:../css/style.css
%!postproc(html): <TITLE> <meta name = "viewport" content = "width = device-width"><TITLE>
%!postproc(html): <TD><B> <TH>
%!postproc(html): </B></TD> </TH>
%!postproc(html): <H1> <H1><a href="../"><IMG src="../doc/Logos/gf0.png"></a>
**GF 3.3.3** was released on 3 March 2012.
What's new? See the [Release notes release-3.3.3.html].
@@ -24,7 +18,7 @@ What's new? See the [Release notes release-3.3.3.html].
===Notes===
The Windows package is installed by just unpacking it anywhere.
The Windows package is installed by just unpacking it anywhere.
It finds the libraries relative to the ``.exe`` file.
%The ``.deb`` packages work on Ubuntu 10.04 and 10.10.
@@ -127,9 +121,3 @@ For more info, see the [GF Developers Guide ../doc/gf-developers.html].
- [GF 3.2 index-3.2.html] (December 2010).
- [GF 3.1.6 index-3.1.6.html] (April 2010).
- [GF 3.1 old-index.html] (December 2009).
--------------------
[www.grammaticalframework.org http://www.grammaticalframework.org]

View File

@@ -1,11 +1,6 @@
Grammatical Framework Download and Installation
%!style:../css/style.css
%!postproc(html): <TD><B> <TH>
%!postproc(html): </B></TD> </TH>
%!postproc(html): <H1> <H1><a href="../"><IMG src="../doc/Logos/gf0.png"></a>
**GF 3.3** was released on 27 October 2011.
What's new? See the [Release notes release-3.3.html].
@@ -27,7 +22,7 @@ More packages might be added later.
===Notes===
The Windows package is installed by just unpacking it anywhere.
The Windows package is installed by just unpacking it anywhere.
It finds the libraries relative to the ``.exe`` file.
%The ``.deb`` packages work on Ubuntu 10.04 and 10.10.
@@ -115,9 +110,3 @@ The above notes for installing from source apply also in this case.
- [GF 3.2 index-3.2.html] (December 2010).
- [GF 3.1.6 index-3.1.6.html] (April 2010).
- [GF 3.1 old-index.html] (December 2009).
--------------------
[www.grammaticalframework.org http://www.grammaticalframework.org]

View File

@@ -1,13 +1,6 @@
Grammatical Framework Download and Installation
%!style:../css/style.css
%!postproc(html): </HEAD> <STYLE>body { color: #333; } li>code,p>code,pre { color: #730; }</STYLE></HEAD>
%!postproc(html): <TITLE> <meta name = "viewport" content = "width = device-width"><TITLE>
%!postproc(html): <TD><B> <TH>
%!postproc(html): </B></TD> </TH>
%!postproc(html): <H1> <H1><a href="../"><IMG src="../doc/Logos/gf0.png"></a>
**GF 3.4** was released on 31 January 2013.
What's new? See the [Release notes release-3.4.html].
@@ -20,14 +13,11 @@ What's new? See the [Release notes release-3.4.html].
| Fedora (32-bit) | [Fedora RPMs /~hallgren/tmp/Fedora/] | ``sudo rpm -i ...``
| Ubuntu (32-bit) | [gf_3.4-1_i386.deb gf_3.4-1_i386.deb] | ``sudo dpkg -i gf_3.4-1_i386.deb``
| Ubuntu (64-bit) | [gf_3.4-1_amd64.deb gf_3.4-1_amd64.deb] | ``sudo dpkg -i gf_3.4-1_amd64.deb``
| Windows | [gf-3.4-bin-windows.zip gf-3.4-bin-windows.zip] |
%| ... | ... | ...
%More binary packages might be added later.
| Windows | [gf-3.4-bin-windows.zip gf-3.4-bin-windows.zip] | -
===Notes===
%The Windows package is installed by just unpacking it anywhere.
%The Windows package is installed by just unpacking it anywhere.
%It finds the libraries relative to the ``.exe`` file.
The ``.deb`` packages work on Ubuntu 12.04, 12.10 and 13.04.
@@ -153,8 +143,3 @@ For more info on working with the GF source code, see the
- [GF 3.2 index-3.2.html] (December 2010).
- [GF 3.1.6 index-3.1.6.html] (April 2010).
- [GF 3.1 old-index.html] (December 2009).
--------------------
[www.grammaticalframework.org http://www.grammaticalframework.org]

View File

@@ -1,13 +1,6 @@
Grammatical Framework Download and Installation
%!style:../css/style.css
%!postproc(html): </HEAD> <STYLE>body { color: #333; } li>code,p>code,pre { color: #730; }</STYLE></HEAD>
%!postproc(html): <TITLE> <meta name = "viewport" content = "width = device-width"><TITLE>
%!postproc(html): <TD><B> <TH>
%!postproc(html): </B></TD> </TH>
%!postproc(html): <H1> <H1><a href="../"><IMG src="../doc/Logos/gf0.png"></a>
**GF 3.5** was released on 6 August 2013.
What's new? See the [Release notes release-3.5.html].
@@ -157,8 +150,3 @@ For more info on working with the GF source code, see the
- [GF 3.2 index-3.2.html] (December 2010).
- [GF 3.1.6 index-3.1.6.html] (April 2010).
- [GF 3.1 old-index.html] (December 2009).
--------------------
[www.grammaticalframework.org http://www.grammaticalframework.org]

View File

@@ -1,13 +1,6 @@
Grammatical Framework Download and Installation
%!style:../css/style.css
%!postproc(html): </HEAD> <STYLE>body { color: #333; } li>code,p>code,pre { color: #730; }</STYLE></HEAD>
%!postproc(html): <TITLE> <meta name = "viewport" content = "width = device-width"><TITLE>
%!postproc(html): <H1> <H1><a href="../"><IMG src="../doc/Logos/gf0.png"></a>
%!postproc(html): <TD><I> <TD><small>
%!postproc(html): </I></TD> </small></TD>
**GF 3.6** was released on 23 June 2014.
What's new? See the [Release notes release-3.6.html].
@@ -177,8 +170,3 @@ For more info on working with the GF source code, see the
- [GF 3.2 index-3.2.html] (December 2010).
- [GF 3.1.6 index-3.1.6.html] (April 2010).
- [GF 3.1 old-index.html] (December 2009).
--------------------
[www.grammaticalframework.org http://www.grammaticalframework.org]

View File

@@ -1,12 +1,6 @@
Grammatical Framework Download and Installation
%!style:../css/notes.css
%!postproc(html): <TITLE> <meta name = "viewport" content = "width = device-width"><TITLE>
%!postproc(html): <H1> <H1><a href="../"><IMG src="../doc/Logos/gf0.png"></a>
%!postproc(html): <TD><I> <TD><small>
%!postproc(html): </I></TD> </small></TD>
**GF 3.7.1** was released on 2 October 2015.
What's new? See the [Release notes release-3.7.1.html].
@@ -46,7 +40,7 @@ The ``.deb`` packages work on Ubuntu 12.04, 14.04 and 15.04.
The packages for Mac OS X should work on at least 10.9, 10.10 and 10.11 (Mavericks, Yosemite and El Capitan).
(*) **Note** that for compatibility with OS X 10.11,
(*) **Note** that for compatibility with OS X 10.11,
``gf-3.7.1.pkg`` will install the ``gf`` executable in ``/usr/local/bin``
instead of ``/usr/bin``, so make sure ``/usr/local/bin`` is in your ``$PATH``.
Also, if you still have an older version of GF installed in ``/usr/bin``,
@@ -180,8 +174,3 @@ For more info on working with the GF source code, see the
- [GF 3.2 index-3.2.html] (December 2010).
- [GF 3.1.6 index-3.1.6.html] (April 2010).
- [GF 3.1 old-index.html] (December 2009).
--------------------
[www.grammaticalframework.org http://www.grammaticalframework.org]

View File

@@ -1,13 +1,6 @@
Grammatical Framework Download and Installation
%!style:../css/style.css
%!postproc(html): </HEAD> <STYLE>body { color: #333; } li>code,p>code,pre { color: #730; }</STYLE></HEAD>
%!postproc(html): <TITLE> <meta name = "viewport" content = "width = device-width"><TITLE>
%!postproc(html): <H1> <H1><a href="../"><IMG src="../doc/Logos/gf0.png"></a>
%!postproc(html): <TD><I> <TD><small>
%!postproc(html): </I></TD> </small></TD>
**GF 3.7** was released on 25 June 2015.
What's new? See the [Release notes release-3.7.html].
@@ -173,8 +166,3 @@ For more info on working with the GF source code, see the
- [GF 3.2 index-3.2.html] (December 2010).
- [GF 3.1.6 index-3.1.6.html] (April 2010).
- [GF 3.1 old-index.html] (December 2009).
--------------------
[www.grammaticalframework.org http://www.grammaticalframework.org]

View File

@@ -1,12 +1,6 @@
Grammatical Framework Download and Installation
%!style:../css/notes.css
%!postproc(html): <TITLE> <meta name = "viewport" content = "width = device-width"><TITLE>
%!postproc(html): <H1> <H1><a href="../"><IMG src="../doc/Logos/gf0.png"></a>
%!postproc(html): <TD><I> <TD><small>
%!postproc(html): </I></TD> </small></TD>
**GF 3.8** was released on 22 June 2016.
What's new? See the [Release notes release-3.8.html].
@@ -49,7 +43,7 @@ Linux distributions.
The packages for Mac OS X should work on at least 10.9, 10.10 and 10.11 (Mavericks, Yosemite and El Capitan).
(*) **Note** that for compatibility with OS X 10.11,
(*) **Note** that for compatibility with OS X 10.11,
``gf-3.8.pkg`` will install the ``gf`` executable in ``/usr/local/bin``
instead of ``/usr/bin``, so make sure ``/usr/local/bin`` is in your ``$PATH``.
Also, if you still have an older version of GF installed in ``/usr/bin``,
@@ -171,8 +165,3 @@ For more info on working with the GF source code, see the
- [GF 3.2 index-3.2.html] (December 2010).
- [GF 3.1.6 index-3.1.6.html] (April 2010).
- [GF 3.1 old-index.html] (December 2009).
--------------------
[www.grammaticalframework.org http://www.grammaticalframework.org]

View File

@@ -1,12 +1,6 @@
Grammatical Framework Download and Installation
%!style:../css/notes.css
%!postproc(html): <TITLE> <meta name = "viewport" content = "width = device-width"><TITLE>
%!postproc(html): <H1> <H1><a href="../"><IMG src="../doc/Logos/gf0.png"></a>
%!postproc(html): <TD><I> <TD><small>
%!postproc(html): </I></TD> </small></TD>
**GF 3.9** was released on 11 August 2017.
What's new? See the [Release notes release-3.9.html].
@@ -18,10 +12,11 @@ What's new? See the [Release notes release-3.9.html].
| macOS | [gf-3.9.pkg gf-3.9.pkg] | //GF+S+C+J+P// | Double-click on the package icon
| macOS | [gf-3.9-bin-intel-mac.tar.gz gf-3.9-bin-intel-mac.tar.gz] | //GF+S+C+J+P// | ``sudo tar -C /usr/local -zxf gf-3.9-bin-intel-mac.tar.gz``
%| Fedora (32-bit) | [Fedora RPMs /~hallgren/tmp/Fedora/] | //GF+S+C+J+P// | ``sudo rpm -i ...``
| Raspian 9.1 | [gf_3.9-1_armhf.deb gf_3.9-1_armhf.deb] | //GF+S+C+J+P// | ``sudo dpkg -i gf_3.9-1_armhf.deb``
| Raspbian 9.1 | [gf_3.9-1_armhf.deb gf_3.9-1_armhf.deb] | //GF+S+C+J+P// | ``sudo dpkg -i gf_3.9-1_armhf.deb``
| Ubuntu (32-bit) | [gf_3.9-1_i386.deb gf_3.9-1_i386.deb] | //GF+S+C+J+P// | ``sudo dpkg -i gf_3.9-1_i386.deb``
| Ubuntu (64-bit) | [gf_3.9-1_amd64.deb gf_3.9-1_amd64.deb] | //GF+S+C+J+P// | ``sudo dpkg -i gf_3.9-1_amd64.deb``
| Windows | [gf-3.9-bin-windows.zip gf-3.9-bin-windows.zip] | //GF+S// | ``unzip gf-3.9-bin-windows.zip``
%| MINGW | [gf-3.9-bin-i686-MINGW32_NT-6.1.tar.gz gf-3.9-bin-i686-MINGW32_NT-6.1.tar.gz] | //GF+S+C// | ``tar -C / gf-3.9-bin-i686-MINGW32_NT-6.1.tar.gz``
%| ... | ... | ... | ...
@@ -176,6 +171,11 @@ The above notes for installing from source apply also in these cases.
For more info on working with the GF source code, see the
[GF Developers Guide ../doc/gf-developers.html].
==Using Stack==
You can also use [Stack https://www.haskellstack.org] to compile GF, just replace ``cabal install`` above
with ``stack install`` (assuming you already have Stack set up).
==Older releases==
- [GF 3.8 index-3.8.html] (June 2016)
@@ -190,8 +190,3 @@ For more info on working with the GF source code, see the
- [GF 3.2 index-3.2.html] (December 2010).
- [GF 3.1.6 index-3.1.6.html] (April 2010).
- [GF 3.1 old-index.html] (December 2009).
--------------------
[www.grammaticalframework.org http://www.grammaticalframework.org]

187
download/index.md Normal file
View File

@@ -0,0 +1,187 @@
---
title: Grammatical Framework Download and Installation
...
**GF 3.10** was released on 2 December 2018.
What's new? See the [release notes](release-3.10.html).
## Binary packages
These binary packages include both the GF core (compiler and runtime) as well as the pre-compiled RGL.
| Platform | Download | Features | How to install |
|:----------------|:---------------------------------------------------|:---------------|:-----------------------------------|
| macOS | [gf-3.10.pkg](gf-3.10.pkg) | GF, S, C, J, P | Double-click on the package icon |
| Ubuntu (32-bit) | [gf\_3.10-2\_i386.deb](gf_3.10-2_i386.deb) | GF, S, C, J, P | `sudo dpkg -i gf_3.10-2_i386.deb` |
| Ubuntu (64-bit) | [gf\_3.10-2\_amd64.deb](gf_3.10-2_amd64.deb) | GF, S, C, J, P | `sudo dpkg -i gf_3.10-2_amd64.deb` |
| Windows | [gf-3.10-bin-windows.zip](gf-3.10-bin-windows.zip) | GF, S | `unzip gf-3.10-bin-windows.zip` |
<!--
| macOS | [gf-3.10-bin-intel-mac.tar.gz](gf-3.10-bin-intel-mac.tar.gz) | GF,S,C,J,P | `sudo tar -C /usr/local -zxf gf-3.10-bin-intel-mac.tar.gz` |
| Raspbian 9.1 | [gf\_3.10-1\_armhf.deb](gf_3.10-1_armhf.deb) | GF,S,C,J,P | `sudo dpkg -i gf_3.10-1_armhf.deb` |
-->
**Features**
- GF = GF shell and grammar compiler
- S = `gf -server` mode
- C = C run-time system
- J/P = Java/Python binding to the C run-time system
### Notes
The Windows package is installed by just unpacking it anywhere. You will
probably need to set the `PATH` and `GF_LIB_PATH` environment variables,
see Inari's notes on [Installing GF on Windows](http://www.grammaticalframework.org/~inari/gf-windows.html#toc3).
The Ubuntu `.deb` packages should work on Ubuntu 16.04 and 18.04 and
similar Linux distributions. The `.deb` packages were updated
to version 3.10-2 after the release of GF 3.10.
(Because of a packaging bug the Resource Grammar Library was missing
in the 3.10-1 packages.)
<!-- The Raspbian `.deb` package was created on a Raspberry Pi 3 and will
probably work on other ARM-based systems running Debian 9 (stretch) or
similar Linux distributions. -->
The packages for macOS (Mac OS X) should work on at least 10.13 and
10.14 (High Sierra and Mojave)
<!-- The Mac OS and Linux `.tar.gz` packages are designed to be installed in
`/usr/local`. You can install them in other locations, but then you need
to set the `GF_LIB_PATH` environment variable:
```
export GF_LIB_PATH=/usr/local/share/gf-3.10/lib
```
where `/usr/local` should be replaced with the path to the location
where you unpacked the package. -->
## Installing the latest release from source
[GF is on Hackage](http://hackage.haskell.org/package/gf), so under
normal circumstances the procedure is fairly simple:
1. Install a recent version of the [Haskell
Platform](http://hackage.haskell.org/platform) (see note below)
2. `cabal update`
3. On Linux: install some C libraries from your Linux distribution (see note below)
4. `cabal install gf`
This installs the GF executable and Haskell libraries, but **does not include the RGL**.
You can also download the source code release from [GitHub](https://github.com/GrammaticalFramework/gf-core/releases),
and follow the instructions below under **Installing from the latest developer source code**.
### Notes
**Installation location**
The above steps installs GF for a single user. The executables are put
in `$HOME/.cabal/bin` (or, with recent versions of the Haskell platform
on Mac OS X, in `$HOME/Library/Haskell/bin`), so it is a good idea to
put a line in your `.bash_profile` or `.profile` to add that directory
to you path:
```
PATH=$HOME/.cabal/bin:$PATH
```
or
```
PATH=$HOME/Library/Haskell/bin:$PATH
```
**Build tools**
In order to compile GF you need the build tools **Alex** and **Happy**.
These can be installed via Cabal, e.g.:
```
cabal install alex happy
```
or obtained by other means, depending on your OS.
**Haskeline**
GF uses [`haskeline`](http://hackage.haskell.org/package/haskeline), which
on Linux depends on some non-Haskell libraries that won't be installed
automatically by cabal, and therefore need to be installed manually.
Here is one way to do this:
- On Ubuntu: `sudo apt-get install libghc-haskeline-dev`
- On Fedora: `sudo yum install ghc-haskeline-devel`
**GHC version**
The GF source code has been updated to compile with GHC 8.4.
Using older versions of GHC (e.g. 8.2, 8.0 and 7.10) should still work too.
## Installing from the latest developer source code
If you haven't already, clone the repository with:
```
git clone https://github.com/GrammaticalFramework/gf-core.git
```
If you've already cloned the repository previously, update with:
```
git pull
```
Then install with:
```
cabal install
```
or, if you're a Stack user:
```
stack install
```
The above notes for installing from source apply also in these cases.
For more info on working with the GF source code, see the
[GF Developers Guide](../doc/gf-developers.html).
## Installing the RGL from source
To install the RGL from source,
you can download a release from [GitHub](https://github.com/GrammaticalFramework/gf-rgl/releases)
or get the latest version by cloning the repository:
```
git clone https://github.com/GrammaticalFramework/gf-rgl.git
```
In both cases, once you have the RGL sources you can install them by running:
```
make
```
in the RGL folder.
This assumes that you already have GF installed.
For more details about building the RGL, see the [RGL README](https://github.com/GrammaticalFramework/gf-rgl/blob/master/README.md).
## Older releases
- [GF 3.9](index-3.9.html) (August 2017)
- [GF 3.8](index-3.8.html) (June 2016)
- [GF 3.7.1](index-3.7.1.html) (October 2015)
- [GF 3.7](index-3.7.html) (June 2015)
- [GF 3.6](index-3.6.html) (June 2014)
- [GF 3.5](index-3.5.html) (August 2013)
- [GF 3.4](index-3.4.html) (January 2013)
- [GF 3.3.3](index-3.3.3.html) (March 2012)
- [GF 3.3](index-3.3.html) (October 2011)
- [GF 3.2.9](index-3.2.9.html) source-only snapshot (September 2011)
- [GF 3.2](index-3.2.html) (December 2010)
- [GF 3.1.6](index-3.1.6.html) (April 2010)

View File

@@ -5,13 +5,13 @@ GF Version 3.1.6 Release Notes
=Installation=
The binaries now work out of the box for each platform and support
completions (file names and parsing), because readline has been
completions (file names and parsing), because readline has been
changed to haskeline.
To compile from source, GHC 6.12 is now required. But GHC is not needed
if the binary executables are used.
Binaries (``.gfo`` and ``.pgf`` files) compiled with GF 3.1 are incompatible
Binaries (``.gfo`` and ``.pgf`` files) compiled with GF 3.1 are incompatible
with 3.1.6 and must either be removed; alternatively, the ``-src`` flag can be
used when compiling.
@@ -24,8 +24,8 @@ Grammar language
- improved support for dependent types (see ``SUMO``, ``nqueens`` in ``examples``)
Shell commands and options (see ``help`` in GF for more information)
- ``eb``: example-based grammar file conversion
Shell commands and options (see ``help`` in GF for more information)
- ``eb``: example-based grammar file conversion
(see ``examples/animals/QuestionI.gf``)
- ``vd = visualize_dependency``: show dependency tree
- ``vp = visualize_parse``: show parse tree
@@ -57,8 +57,3 @@ Internal
Javascript generation is not updated to the new PGF format.
[GF 3.1 old-index.html] should still be used for building Javascript applications.

66
download/release-3.10.md Normal file
View File

@@ -0,0 +1,66 @@
---
title: GF 3.10 Release Notes
date: 2 December 2018
...
## Installation
See the [download page](index.html).
## What's new
In this release, the GF "core" (compiler and runtimes) and RGL have been split into separate repositories.
The binary packages on the downloads page contain both GF and the RGL, but the sources are now separate:
[gf-core](https://github.com/GrammaticalFramework/gf-core) and
[gf-rgl](https://github.com/GrammaticalFramework/gf-rgl).
Over 300 changes have been pushed to GF and over 600 changes have been made to the RGL
since the release of GF 3.9 in August 2017.
## General
- Travis integration:
GF [![Build Status](https://travis-ci.org/GrammaticalFramework/gf-core.svg?branch=master)](https://travis-ci.org/GrammaticalFramework/gf-core) and
RGL [![Build Status](https://travis-ci.org/GrammaticalFramework/gf-rgl.svg?branch=master)](https://travis-ci.org/GrammaticalFramework/gf-rgl)
- A lot of bug fixes and repository cleanup, including things moved to new repositories:
- [Phrasebook](https://github.com/GrammaticalFramework/gf-contrib/tree/master/phrasebook)
- [Wide coverage translator](https://github.com/GrammaticalFramework/wide-coverage)
- [Mobile apps](https://github.com/GrammaticalFramework/gf-offline-translator)
- [gftest](https://github.com/GrammaticalFramework/gftest)
- [gf-mode](https://github.com/GrammaticalFramework/gf-emacs-mode) for Emacs
- [RGL browser](https://github.com/GrammaticalFramework/rgl-source-browser) (live [here](http://www.grammaticalframework.org/~john/rgl-browser/))
- A fresh look for the GF website.
## GF compiler and run-time library
- Extensive improvements in the C runtime and bindings to it from Python, Java, Haskell, C#
- A GF shell which uses the C runtime
- Better error messages
- GF now has a Stack configuration file
- The compiler source code has been updated for compatibility with GHC 8.4.3.
- `GF_LIB_PATH` can now be `path1:path2:path3`, not just `path1`
- Add TypeScript type definitions for `gflib.js`
- New compiler/shell options
- added option `-output-format=java` for producing code for embedded grammars in Java
- `rf -paragraphs`
- `linearize -tabtreebank`
- A new function called `completions` is added in the Haskell runtime and used in PGFService. This makes the extraction of completions more platform independent
## Resource Grammar Library
- [Bash build script](https://github.com/GrammaticalFramework/gf-rgl/blob/master/Setup.sh), for building the RGL without Haskell
- [Windows build script](https://github.com/GrammaticalFramework/gf-rgl/blob/master/Setup.bat), for building the RGL without Haskell on a regular Windows command shell
- New languages:
- Basque
- Portuguese
- Big progress with Arabic, Turkish, Persian
- Introduction of `Extend` module to combine the functions of `Extra` and `Extensions` in a more disciplined way
- Various fixes for several languages.
- Various fixes in the translation dictionaries.
## Apps and Cloud services
- Sort list of public grammars by age by default
- Browser compatibility fixes
- Allow public grammars to be deleted in more cases
- Show grammar comments in the list of public grammars

View File

@@ -1,9 +1,6 @@
GF Version 3.2 Release Notes
December 2010
%!style:../css/style.css
%!postproc(html): <H1> <H1><IMG src="../doc/Logos/gf0.png">
==Installation==
See the [download page http://www.grammaticalframework.org/download/index.html].
@@ -34,8 +31,3 @@ See the [download page http://www.grammaticalframework.org/download/index.html].
- GF compiler: GPL
- Run-time libraries and Resource Grammar Library: LGPL + BSD
--------------------
[www.grammaticalframework.org http://www.grammaticalframework.org]

View File

@@ -1,10 +1,6 @@
GF Version 3.3.3 Release Notes
March 2012
%!style:../css/style.css
%!postproc(html): <TITLE> <meta name = "viewport" content = "width = device-width"><TITLE>
%!postproc(html): <H1> <H1><IMG src="../doc/Logos/gf0.png">
==Installation==
See the [download page http://www.grammaticalframework.org/download/index.html].
@@ -25,8 +21,3 @@ See the [download page http://www.grammaticalframework.org/download/index.html].
- Fix for a bug that prevented the shell commands ``abstract_info``,
``generate_random`` and ``generate_trees`` from working properly.
- Various other small improvements and bug fixes.
--------------------
[www.grammaticalframework.org http://www.grammaticalframework.org]

View File

@@ -1,17 +1,13 @@
GF Version 3.3 Release Notes
October 2011
%!style:../css/style.css
%!postproc(html): <TITLE> <meta name = "viewport" content = "width = device-width"><TITLE>
%!postproc(html): <H1> <H1><IMG src="../doc/Logos/gf0.png">
==Installation==
See the [download page http://www.grammaticalframework.org/download/index.html].
==New features==
- Source language extension: it is now possible to override the oper definitions in an interface, by using the
- Source language extension: it is now possible to override the oper definitions in an interface, by using the
header syntax ``instance Foo of Bar - [f,g,h]``.
- New functionalities in GF shell commands (more information with ``help`` command-name).
- ``aw`` = ``align_words`` option ``-giza`` prints word alignments in Giza++ format.
@@ -29,8 +25,3 @@ See the [download page http://www.grammaticalframework.org/download/index.html].
and the web-based grammar editor.
- Faster grammar compilation (also included in the GF 3.2.9 source-only
snapshot).
--------------------
[www.grammaticalframework.org http://www.grammaticalframework.org]

View File

@@ -1,10 +1,6 @@
GF Version 3.4 Release Notes
January 2013
%!style:../css/style.css
%!postproc(html): <TITLE> <meta charset="UTF-8"><meta name = "viewport" content = "width = device-width"> <TITLE>
%!postproc(html): <H1> <H1><a href="../"><IMG src="../doc/Logos/gf0.png"></a>
==Installation==
See the [download page http://www.grammaticalframework.org/download/index.html].
@@ -46,8 +42,3 @@ See the [download page http://www.grammaticalframework.org/download/index.html].
- Some new functionality in the web-based grammar editor, e.g. preliminary
support for public grammars.
- Various other small improvements and bug fixes.
--------------------
[www.grammaticalframework.org http://www.grammaticalframework.org]

View File

@@ -1,10 +1,6 @@
GF 3.5 Release Notes
August 2013
%!style:../css/style.css
%!postproc(html): <TITLE> <meta charset="UTF-8"><meta name = "viewport" content = "width = device-width"> <TITLE>
%!postproc(html): <H1> <H1><a href="../"><IMG src="../doc/Logos/gf0.png"></a>
==Installation==
See the [download page http://www.grammaticalframework.org/download/index.html].
@@ -70,7 +66,3 @@ of GF 3.4.
[``network-2.4.1.1`` https://github.com/haskell/network/commit/f2168b1f8978b4ad9c504e545755f0795ac869ce].
- Various other small improvements and bug fixes.
%- [...]
--------------------
[www.grammaticalframework.org http://www.grammaticalframework.org]

View File

@@ -1,10 +1,6 @@
GF 3.6 Release Notes
June 2014
%!style:../css/style.css
%!postproc(html): <TITLE> <meta charset="UTF-8"><meta name = "viewport" content = "width = device-width"> <TITLE>
%!postproc(html): <H1> <H1><a href="../"><IMG src="../doc/Logos/gf0.png"></a>
==Installation==
See the [download page http://www.grammaticalframework.org/download/index.html].
@@ -26,7 +22,7 @@ Closed [issues http://code.google.com/p/grammatical-framework/issues/list]:
as ``--# -coding=``//enc//, instead of ``flags coding=``//enc//.
See the separate document
[GF character encoding changes encoding-change.html] for more details.
- Record update: in record objects (but not types) of form ``r ** s``, the values assigned
- Record update: in record objects (but not types) of form ``r ** s``, the values assigned
in ``s`` now overwrite those in ``r``. In previous versions, record extensions with
overlapping assignments in ``r`` and ``s`` were not supported, and their behaviour was
unpredictable.
@@ -107,8 +103,3 @@ Closed [issues http://code.google.com/p/grammatical-framework/issues/list]:
- ``c-wordforword``: this works as ``c-translate`` but does a
word-for-word lookup to create a (potentially very low quality)
translation that can be used if all else fails.
--------------------
[www.grammaticalframework.org http://www.grammaticalframework.org]

View File

@@ -1,10 +1,6 @@
GF 3.7.1 Release Notes
October 2015
%!style:../css/notes.css
%!postproc(html): <TITLE> <meta charset="UTF-8"><meta name = "viewport" content = "width = device-width"> <TITLE>
%!postproc(html): <H1> <H1><a href="../"><IMG src="../doc/Logos/gf0.png"></a>
==Installation==
See the [download page http://www.grammaticalframework.org/download/index.html].
@@ -18,10 +14,10 @@ Over 170 changes have been pushed to the source repository since
====New features and notable changes====
- GF shell: ``cc -trace`` (preliminary): you can now do things like
- GF shell: ``cc -trace`` (preliminary): you can now do things like
``cc -trace mkV "debug"``
to see a trace of all opers with their arguments and results during the
computation of ``mkV "debug"``.
@@ -29,7 +25,7 @@ Over 170 changes have been pushed to the source repository since
from the GF shell by starting GF with ``gf -cshell`` or ``gf -crun``.
Only limited functionality is available when running the shell in these
modes (use the ``help`` command in the shell for details):
- You can only import ``.pgf`` files, not source files.
- The ``-retain`` flag can not be used and the commands that require it to
work are not available.
@@ -77,8 +73,3 @@ Over 170 changes have been pushed to the source repository since
you can leave ``&+`` uninterpreted instead of gluing the adjacent tokens.
This means that the output is left in a format that can be parsed in
a subsequent request.
--------------------
[www.grammaticalframework.org http://www.grammaticalframework.org]

View File

@@ -1,10 +1,6 @@
GF 3.7 Release Notes
June 2015
%!style:../css/style.css
%!postproc(html): <TITLE> <meta charset="UTF-8"><meta name = "viewport" content = "width = device-width"> <TITLE>
%!postproc(html): <H1> <H1><a href="../"><IMG src="../doc/Logos/gf0.png"></a>
==Installation==
See the [download page http://www.grammaticalframework.org/download/index.html].
@@ -40,7 +36,7 @@ Over 800 changes have been pushed to the source repository since
``BIND``, ``SOFT_BIND``, ``SOFT_SPACE``, ``CAPIT``, ``ALL_CAPIT`` and
``nonExist``.
- It is now possible to define callbacks for literals from the Haskell
binding to the C runtime. This is used for instance in
binding to the C runtime. This is used for instance in
the Wide Coverage translator on the Web.
@@ -103,8 +99,3 @@ Over 800 changes have been pushed to the source repository since
unused for 24 hours, to keep memory use down in long running servers.
- PGF service: limit the number of parallel calls to the C run-time parse
function to 4 by default. The limit can be changed with the ``-j`` flag.
--------------------
[www.grammaticalframework.org http://www.grammaticalframework.org]

View File

@@ -1,10 +1,6 @@
GF 3.8 Release Notes
June 2016
%!style:../css/notes.css
%!postproc(html): <TITLE> <meta charset="UTF-8"><meta name = "viewport" content = "width = device-width"> <TITLE>
%!postproc(html): <H1> <H1><a href="../"><IMG src="../doc/Logos/gf0.png"></a>
==Installation==
See the [download page http://www.grammaticalframework.org/download/index.html].
@@ -25,7 +21,7 @@ Roughly 400 changes have been pushed to the source repository since
[universal dependency http://universaldependencies.org/] diagrams
in various formats, see ``help vd``.
- The C runtime now includes an experimental library for managing
and querying ontologies built on top of the abstract syntax of
and querying ontologies built on top of the abstract syntax of
a grammar. Since the ontology is based on an abstract syntax,
it is language independent by design. For now the library is
only used in the GF Offline Translator. The library uses
@@ -100,7 +96,3 @@ Roughly 400 changes have been pushed to the source repository since
translations in the domain they cover.
You can change the order in which the selected grammars are tried
by dragging them up and down in the list.
--------------------
[www.grammaticalframework.org http://www.grammaticalframework.org]

View File

@@ -1,10 +1,6 @@
GF 3.9 Release Notes
August 2017
%!style:../css/notes.css
%!postproc(html): <TITLE> <meta charset="UTF-8"><meta name = "viewport" content = "width = device-width"> <TITLE>
%!postproc(html): <H1> <H1><a href="../"><IMG src="../doc/Logos/gf0.png"></a>
==Installation==
See the [download page http://www.grammaticalframework.org/download/index.html].
@@ -36,7 +32,7 @@ very innefficient for some grammars.
- A new .NET binding for the GF runtime is available.
- The API in the Java binding is extended and it covers more from
- The API in the Java binding is extended and it covers more from
the full functionality of the C runtime.
@@ -66,8 +62,3 @@ the full functionality of the C runtime.
- PGF service: support for language-specific depencency configurations in
``command=deptree``.
--------------------
[www.grammaticalframework.org http://www.grammaticalframework.org]

BIN
favicon.ico Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 15 KiB

View File

@@ -1,5 +1,5 @@
name: gf
version: 3.9-git
version: 3.10.3-git
cabal-version: >= 1.22
build-type: Custom
@@ -11,7 +11,7 @@ description: GF, Grammatical Framework, is a programming language for multilingu
homepage: http://www.grammaticalframework.org/
bug-reports: https://github.com/GrammaticalFramework/gf-core/issues
maintainer: Thomas Hallgren
tested-with: GHC==7.6.3, GHC==7.8.3, GHC==7.10.3, GHC==8.0.2
tested-with: GHC==7.10.3, GHC==8.0.2, GHC==8.2.2, GHC==8.4.3
data-dir: src
data-files:
@@ -42,7 +42,7 @@ data-files:
custom-setup
setup-depends:
base,
Cabal >=1.4.0.0,
Cabal >=1.22.0.0,
directory,
filepath,
process >=1.0.1.1
@@ -67,11 +67,6 @@ flag network-uri
-- Description: Make -new-comp the default
-- Default: True
flag custom-binary
Description: Use a customised version of the binary package
Default: True
Manual: True
flag c-runtime
Description: Include functionality from the C run-time library (which must be installed already)
Default: False
@@ -86,26 +81,25 @@ Library
random,
pretty,
mtl,
exceptions
exceptions,
ghc-prim
hs-source-dirs: src/runtime/haskell
if flag(custom-binary)
other-modules:
-- not really part of GF but I have changed the original binary library
-- and we have to keep the copy for now.
Data.Binary
Data.Binary.Put
Data.Binary.Get
Data.Binary.Builder
Data.Binary.IEEE754
else
build-depends: binary, data-binary-ieee754
other-modules:
-- not really part of GF but I have changed the original binary library
-- and we have to keep the copy for now.
Data.Binary
Data.Binary.Put
Data.Binary.Get
Data.Binary.Builder
Data.Binary.IEEE754
--ghc-options: -fwarn-unused-imports
--if impl(ghc>=7.8)
-- ghc-options: +RTS -A20M -RTS
ghc-prof-options: -fprof-auto
extensions:
if impl(ghc>=8.6)
Default-extensions: NoMonadFailDesugaring
exposed-modules:
PGF
@@ -149,8 +143,8 @@ Library
---- GF compiler as a library:
build-depends: filepath, directory, time, time-compat, old-locale,
process, haskeline, parallel>=3
build-depends: filepath, directory>=1.2, time,
process, haskeline, parallel>=3, json
hs-source-dirs: src/compiler
exposed-modules:
@@ -158,6 +152,7 @@ Library
GF.Support
GF.Text.Pretty
GF.Text.Lexing
GF.Grammar.Canonical
other-modules:
GF.Main GF.Compiler GF.Interactive
@@ -196,7 +191,10 @@ Library
GF.Compile.PGFtoJava
GF.Haskell
GF.Compile.ConcreteToHaskell
GF.Compile.GrammarToCanonical
GF.Grammar.CanonicalJSON
GF.Compile.PGFtoJS
GF.Compile.PGFtoJSON
GF.Compile.PGFtoProlog
GF.Compile.PGFtoPython
GF.Compile.ReadFiles
@@ -275,7 +273,7 @@ Library
cpp-options: -DC_RUNTIME
if flag(server)
build-depends: httpd-shed>=0.4.0.3, network>=2.3 && <2.7, json,
build-depends: httpd-shed>=0.4.0.3, network>=2.3 && <2.7,
cgi>=3001.2.2.0
if flag(network-uri)
build-depends: network-uri>=2.6, network>=2.6

View File

@@ -1,418 +1,390 @@
<!DOCTYPE html>
<HTML>
<HEAD>
<TITLE>GF - Grammatical Framework</TITLE>
<meta charset="UTF-8">
<link rel="stylesheet" href="css/newstyle.css" title="GF">
<link rel="alternate" href="https://github.com/GrammaticalFramework/gf-core/" title="GF GitHub repository">
<meta name = "viewport" content = "width = device-width">
<script type="text/javascript">
function sitesearch() {
var q=document.forms[0].q.value;
var site=" site:www.grammaticalframework.org";
var search=encodeURIComponent(q+site)
document.location.href="http://www.google.com/search?q="+search
return false;
}
</script>
<meta name="keywords" content="machine translation">
</HEAD>
<!doctype html>
<html lang="en">
<head>
<meta charset="utf-8">
<body class=new>
<title>GF - Grammatical Framework</title>
<meta name="keywords" content="machine translation">
<div class="header sky blue">
<img class="gflogo" src="doc/Logos/gf1.svg" alt="">
<H1>Grammatical Framework</H1>
<small class=tagline>A programming language for multilingual grammar applications</small>
<meta name="viewport" content="width=device-width, initial-scale=1, shrink-to-fit=no">
<link rel="stylesheet" href="https://stackpath.bootstrapcdn.com/bootstrap/4.1.3/css/bootstrap.min.css" integrity="sha384-MCw98/SFnGE8fJT3GXwEOngsV7Zt27NXFoaoApmYm81iuXoPkFOJwJ8ERdknLPMO" crossorigin="anonymous">
<link rel="stylesheet" href="https://use.fontawesome.com/releases/v5.4.2/css/all.css" integrity="sha384-/rXc/GQVaYpyDdyxK+ecHPVYJSN9bmVFBvjA/9eOB+pb3F2w2N6fc5qB9Ew5yIns" crossorigin="anonymous">
<link rel="alternate" href="https://github.com/GrammaticalFramework/gf-core/" title="GF GitHub repository">
</head>
<body>
<div class="container-fluid my-5" style="max-width:1200px">
<div class="text-center">
<img style="height:250px" src="doc/Logos/gf1.svg" alt="GF Logo">
<h1 class="display-4" style="text-shadow: 1px 1px 5px #999;">Grammatical Framework</h1>
<h4 class="text-black-50">A programming language for multilingual grammar applications</h4>
</div>
<div class=menu>
<div class="row my-4">
<div class=links>
<h4>Use GF</h4>
<ul>
<li><a href="http://cloud.grammaticalframework.org/">GF Cloud<img class=right src="src/www/P/gf-cloud.png" alt="GF Cloud Service" title="GF Cloud Service"></a>
<li><A HREF="demos/index.html">Other Demos</A>
</ul>
<ul>
<li><A HREF="http://www.grammaticalframework.org/download/index.html"><b>Download GF</b></A>
<li><a href="doc/gf-editor-modes.html">GF Editor Modes</a>
</ul>
<div class="col-sm-6 col-md-3">
<h3>Get started</h3>
<ul class="mb-2">
<li><a href="https://www.youtube.com/watch?v=x1LFbDQhbso">Google Tech Talk</a></li>
<li>
<a href="http://cloud.grammaticalframework.org/">
GF Cloud
<img src="http://www.grammaticalframework.org/src/www/P/gf-cloud.png" style="height:30px" class="ml-2" alt="Cloud logo">
</a>
</li>
<li>
<a href="doc/tutorial/gf-tutorial.html">Tutorial</a>
/
<a href="lib/doc/rgl-tutorial/index.html">RGL Tutorial</a>
</li>
</ul>
<ul>
<li><A HREF="http://groups.google.com/group/gf-dev">User Group</A>
<li><a href="https://github.com/GrammaticalFramework/gf-core/issues">Bug Reports</a>
(<a href="http://code.google.com/p/grammatical-framework/issues/list">old</a>)
</ul>
</div>
<a href="download/index.html" class="btn btn-primary ml-3">
<i class="fas fa-download mr-1"></i>
Download GF
</a>
</div>
<div class=links>
<h4>Learn GF</h4>
<ul>
<li><a href="https://www.youtube.com/watch?v=x1LFbDQhbso">Google Tech Talk</a>
<li><A HREF="doc/gf-quickstart.html">QuickStart</A>
<li><A HREF="doc/gf-reference.html">QuickRefCard</A>
<li><A HREF="doc/gf-shell-reference.html">GF Shell Reference</A>
<li><a href="http://school.grammaticalframework.org/"><b>GF Summer School</b></a>
</ul>
<ul>
<li><A HREF="gf-book">The GF Book</A>
<li><A HREF="doc/tutorial/gf-tutorial.html">GF Tutorial</A>
<li><A HREF="doc/gf-refman.html">Reference Manual</A>
<li><A HREF="http://www.molto-project.eu/sites/default/files/MOLTO_D2.3.pdf">Best Practices</A> <small>[PDF]</small>
</ul>
<ul>
<li><A HREF="lib/doc/synopsis.html">Library Synopsis</A>
<li><A HREF="doc/gf-lrec-2010.pdf">Library Tutorial</A> <small>[PDF]</small>
<li><A HREF="http://www.postcrashgames.com/gf_world/">Coverage Map</A>
</ul>
<div class="col-sm-6 col-md-3">
<h3>Learn more</h3>
</div>
<div class=links>
<h4>Develop GF</h4>
<ul>
<li><a href="doc/gf-developers.html">GF Developers Guide</a>
<li><A HREF="https://github.com/GrammaticalFramework/">GF on GitHub</A>
<li><a href="/~hallgren/gf-experiment/browse/">Browse Source Code</a>
<li><A HREF="doc/gf-people.html">Authors</A>
</ul>
<h4>Develop Applications</h4>
<ul>
<li><a href="http://hackage.haskell.org/package/gf-3.9/docs/PGF.html">PGF library API (Old Runtime)</a>
<li><a href="doc/runtime-api.html">PGF library API (New Runtime)</a>
<li><a href="src/ui/android/README">GF on Android (new)</a>
<li><A HREF="/android/">GF on Android (old) </A>
</ul>
</div>
<div class=links>
<h4>Related to GF</h4>
<ul>
<li><A HREF="doc/gf-bibliography.html">Publications</A>
<li><A HREF="http://remu.grammaticalframework.org/">The REMU Project</A>
<li><A HREF="http://www.molto-project.eu">The MOLTO Project</A>
<li><a href="http://en.wikipedia.org/wiki/Grammatical_Framework">GF on Wikipedia</a>
<li><p><a href="Http://www.digitalgrammars.com/">Digital Grammars AB</a>
</ul>
</div>
</div>
<ul class="mb-2">
<li><a href="gf-book">The GF Book</a></li>
<li><a href="doc/gf-refman.html">Reference Manual</a></li>
<li><a href="doc/gf-shell-reference.html">Shell Reference</a></li>
<li><a href="http://www.molto-project.eu/sites/default/files/MOLTO_D2.3.pdf">Best Practices</a> <small>[PDF]</small></li>
</ul>
<a href="lib/doc/synopsis/index.html" class="btn btn-primary ml-3">
<i class="fab fa-readme mr-1"></i>
RGL Synopsis
</a>
</div>
<script type="text/javascript">
document.write('<div style="float: right; margin-top: 3ex;"> <form onsubmit="return sitesearch()" method=get action="http://www.google.com/search"> <input type=search name="q" placeholder="site search"> <input type=submit value="Search"> </form></div>')
</script>
<div class="col-sm-6 col-md-3">
<h3>Develop</h3>
<ul class="mb-2">
<li><a href="doc/gf-developers.html">Developers Guide</a></li>
<!-- <li><a href="/~hallgren/gf-experiment/browse/">Browse Source Code</a></li> -->
<li><a href="http://hackage.haskell.org/package/gf/docs/PGF.html">PGF library API (Haskell runtime)</a></li>
<li><a href="doc/runtime-api.html">PGF library API (C runtime)</a></li>
<li><a href="http://hackage.haskell.org/package/gf/docs/GF.html">GF compiler API</a></li>
<!-- <li><a href="src/ui/android/README">GF on Android (new)</a></li>
<li><a href="/android/">GF on Android (old) </a></li> -->
<li><a href="doc/gf-editor-modes.html">Text Editor Support</a></li>
</ul>
</div>
<H2 class=noclear>News</H2>
<div class=news2>
<table class=news>
<tr><td>2018-07-25:<td>The GF repository has been split in two:
<a href="https://github.com/GrammaticalFramework/gf-core">gf-core</a> and
<a href="https://github.com/GrammaticalFramework/gf-rgl">gf-rgl</a>.
The original <a href="https://github.com/GrammaticalFramework/GF">GF</a> repository is now archived.
<tr><td>2017-08-11:<td><strong>GF 3.9 released!</strong>
<a href="download/release-3.9.html">Release notes</a>.
<tr><td>2017-06-29:<td>GF is moving to <a href="https://github.com/GrammaticalFramework/GF/">GitHub</a>!
<tr><td>2017-03-13:<td><strong>GF Summer School in Riga (Latvia), 14-25 August 2017</strong>
<a href="http://school.grammaticalframework.org/2017/">Summer
School web page</a>.
<tr><td>2016-09-07:<td><strong>Google Tech Talk on GF</strong> <a
href="https://www.youtube.com/watch?v=x1LFbDQhbso">on Youtube</a>.
<tr><td>2016-07-05:<td>GitHub mirror temporarily not updated, due to server migration.
<tr><td>2016-06-22:<td><strong>GF 3.8 released!</strong>
<a href="download/release-3.8.html">Release notes</a>.
<tr><td>2015-06-21:<td><strong>Summer School in Rule-Based Machine
Translation in Alacant/Alicante (Spain), 11-21 July 2016</strong>
featuring GF, Apertium, Matxin, and TectoMT.
<a href="http://xixona.dlsi.ua.es/rbmt-summer-school/2016/">Summer
School web page</a>.
<tr><td>2016-06-14:<td>New resource grammar language: Nynorsk.
<tr><td>2015-10-02:<td><strong>GF 3.7.1 released!</strong>
<a href="download/release-3.7.1.html">Release notes</a>.
<tr><td>2015-06-25:<td><strong>GF 3.7 released!</strong>
<a href="download/release-3.7.html">Release notes</a>.
<tr><td>2015-03-13:<td>New resource grammar language: Mongolian.
See <a href="lib/doc/synopsis.html">library synopsis</a>.
<tr><td>2015-02-09:<td><strong>GF Summer School in Gozo (Malta), 13-24 July 2015</strong>
<a href="http://school.grammaticalframework.org/2015/">Summer
School web page</a>.
<tr><td>2014-06-23:<td><strong>GF 3.6 released!</strong>
<a href="download/release-3.6.html">Release notes</a>.
<tr><td>2014-03-11:
<td>A company for commercial applications of GF has been founded:
<a href="http://www.digitalgrammars.com/">Digital Grammars</a>.
<tr><td>2013-11-25:
<td>The default character encoding in GF grammar files will be changed
from Latin-1 to UTF-8. See
<a href="download/encoding-change.html">GF character encoding changes</a>
for details.
<tr><td>2013-10-18:<td>New resource grammar language: Estonian.
See <a href="lib/doc/synopsis.html">library synopsis</a>.
<tr><td>2013-09-18:<td>New <a href="https://github.com/GrammaticalFramework/gf-contrib">GF contributions repository</a>, hosted on GitHub.
<tr><td>2013-08-06:<td><strong>GF 3.5 released!</strong>
<a href="download/release-3.5.html">Release notes</a>.
<tr><td>2013-07-26:<td>Started a page with <A HREF="lib/doc/rgl-publications.html">RGL Documentation and Publications</A>.
<tr><td>2013-06-24:<td>We are now running the IRC channel <a href="https://webchat.freenode.net/?channels=gf"><strong><code>#gf</code></strong></a> on the Freenode network.
<tr><td>2013-06-19:<td>New resource grammar language: Maltese.
See <a href="lib/doc/synopsis.html">library synopsis</a>.
<tr><td>2013-04-25:<td>New resource grammar language: Greek.
See <a href="lib/doc/synopsis.html">library synopsis</a>.
<tr><td>2013-01-31:<td><strong>GF 3.4 released!</strong>
<a href="download/release-3.4.html">Release notes</a>.
<tr><td>2012-12-10:<td>
<a href="http://www.postcrashgames.com/gf_world/">Resource Grammar Library
coverage map</a>, created by Tommi Nieminen.
<!--
<tr><td>2012-11-18:<td>
<A HREF="http://school.grammaticalframework.org/2013">GF Summer School</A>
in Frauenchiemsee, 18-30 August 2013.
<tr><td>2012-11-18:<td>New resource grammar language: Chinese.
See <a href="lib/doc/synopsis.html">library synopsis</a>.
Complete but not yet perfect.
<tr><td>2012-06-29:<td>GF sources now mirrored in GitHub, with change
statistics and other browsing features.
See <a href="https://github.com/GrammaticalFramework/GF/"><tt>github.com/GrammaticalFramework/GF</tt></a>
<tr><td>2012-05-07:<td>New resource grammar language: Japanese.
See <a href="lib/doc/synopsis.html">library synopsis</a>.
<tr><td>2012-03-23:<td>There will be a
<a href="gf-tutorial-icfp-2012/">GF tutorial at ICFP 2012</a>
in Copenhagen.
<tr><td>2012-03-03:<td><strong>GF 3.3.3 released!</strong>
<a href="download/release-3.3.3.html">Release notes</a>.
<tr><td>2012-02-24:<td>New resource grammar languages: Hindi, Sindhi.
See <a href="lib/doc/synopsis.html">library synopsis</a>.
<tr><td>2011-12-29:<td>New resource grammar languages: Latvian, Thai.
See <a href="lib/doc/synopsis.html">library synopsis</a>.
<tr><td>2011-10-27:<td><strong>GF 3.3 released!</strong>
<a href="download/release-3.3.html">Release notes</a>.
<tr><td>2011-09-20:<td>There is now a page collecting
<a href="doc/gf-editor-modes.html">editor modes for GF</a>.
Contributions are welcome!
<tr><td>2011-09-12:<td><strong>GF 3.2.9</strong> source snapshot with faster grammar compilation available. See <a href="download/index.html">Downloads</a>.
<tr><td>2011-04-22:<td><a href="android/tutorial/">JPGF Android Tutorial</a> added.
<tr><td>2011-04-15:<td>The <a href="gf-book">GF Book</a> is available.
<tr><td>2011-01-13:<td><a href="http://www.molto-project.eu/node/1177">Phrasedroid
available on the Android Market</a>.
<tr><td>2011-01-04:<td>GF is part of the
<a href="http://www.clt.gu.se/clt-toolkit">CLT Toolkit</a>.
<tr><td>2010-12-23:<td><strong>GF 3.2 released!</strong>
<a href="download/release-3.2.html">Release notes</a>.
-->
</table>
<div class="col-sm-6 col-md-3">
<h3>Contribute</h3>
<ul class="mb-2">
<li><a href="http://groups.google.com/group/gf-dev">Mailing List</a></li>
<li><a href="https://github.com/GrammaticalFramework/gf-core/issues">Issue Tracker</a></li>
<li><a href="doc/gf-people.html">Authors</a></li>
<li><a href="http://school.grammaticalframework.org/2018/">Summer School</a></li>
</ul>
<a href="https://github.com/GrammaticalFramework/" class="btn btn-primary ml-3">
<i class="fab fa-github mr-1"></i>
GF on GitHub
</a>
</div>
</div>
<H2>What is GF</H2>
<P>
<h2>What is GF?</h2>
<p>
GF, Grammatical Framework, is a programming language for
<B>multilingual grammar applications</B>. It is
</P>
<UL>
<LI>a <B>special-purpose language for grammars</B>, like
<strong>multilingual grammar applications</strong>. It is
</p>
<ul>
<li>a <strong>special-purpose language for grammars</strong>, like
<a href="http://dinosaur.compilertools.net/yacc/">YACC</a>,
<a href="http://www.gnu.org/software/bison/">Bison</a>,
<a href="http://www.haskell.org/happy/">Happy</a>,
<a href="http://bnfc.digitalgrammars.com/">BNFC</a>,
but not restricted to programming languages
<LI>a <B>functional programming language</B>, like
</li>
<li>a <strong>functional programming language</strong>, like
<a href="http://www.haskell.org/">Haskell</a>,
<a href="http://en.wikipedia.org/wiki/Lisp_(programming_language)">Lisp</a>,
<a href="http://ocaml.org/">OCaml</a>,
<a href="http://www.smlnj.org/">SML</a>,
<a href="http://schemers.org/">Scheme</a>,
but specialized to grammar writing
<LI>a <B>development platform for natural language grammars</B>, like
</li>
<li>a <strong>development platform for natural language grammars</strong>, like
<a href="http://moin.delph-in.net/LkbTop">LKB</a>,
<a href="http://www2.parc.com/isl/groups/nltt/xle/">XLE</a>,
<a href="http://www.issco.unige.ch/en/research/projects/regulus/news.shtml">Regulus</a>,
but based on functional programming and type theory
<LI>a <B>categorial grammar formalism</B>, like
</li>
<li>a <strong>categorial grammar formalism</strong>, like
<a href="http://www.loria.fr/equipes/calligramme/acg/">ACG</a>,
<a href="http://openccg.sourceforge.net/">CCG</a>,
but specialized for multilingual grammars,
<LI>a <B>logical framework</B>, like
</li>
<li>a <strong>logical framework</strong>, like
<a href="http://wiki.portal.chalmers.se/agda/pmwiki.php">Agda</a>,
<a href="http://coq.inria.fr/">Coq</a>,
<a href="http://www.cl.cam.ac.uk/research/hvg/Isabelle/">Isabelle</a>,
but equipped with concrete syntax in addition to logic
<li>a <b>platform for machine translation</b>, like
</li>
<li>a <strong>platform for machine translation</strong>, like
<a href="http://www.statmt.org/moses/">Moses</a>,
<a href="http://www.apertium.org/">Apertium</a>,
but based on deep structural analysis (and usually applied for
limited fragments of language).
</UL>
</li>
</ul>
<P>
<p>
Don't worry if you don't know most of the references above - but if you do know at
least one, it may help you to get a first idea of what GF is.
</P>
<H2>Applications</H2>
<P>
GF can be used for building
</P>
<UL>
<LI><A HREF="http://cloud.grammaticalframework.org/translator/">translation systems</A>
<LI><A HREF="http://cloud.grammaticalframework.org/minibar/minibar.html">multilingual web gadgets</A>
<LI><A HREF="http://www.cs.chalmers.se/~hallgren/Alfa/Tutorial/GFplugin.html">natural-language interfaces</A>
<LI><A HREF="http://www.youtube.com/watch?v=1bfaYHWS6zU">dialogue systems</A>
<LI><A HREF="lib/doc/synopsis.html">natural language resources</A>
</UL>
<H2>Availability</H2>
<P>
GF is <B>open-source</B>, licensed under <A HREF="LICENSE">GPL</A> (the program) and
<A HREF="./LICENSE">LGPL</A> and <A HREF="./LICENSE">BSD</A> (the libraries). It
is available for
</P>
<UL>
<LI>Linux
<LI>Mac OS X
<LI>Windows
<li>Android mobile platform (via Java; runtime)
<LI>via compilation to JavaScript, almost any platform that has a web browser (runtime)
</UL>
<H2>Projects</H2>
<P>
GF was first created in 1998 at
<A HREF="http://www.xrce.xerox.com/">Xerox Research Centre Europe</A>,
Grenoble, in the project
Multilingual Document Authoring. At Xerox, it was used for prototypes including
a restaurant phrase book,
a database query system,
a formalization of an alarm system instructions with translations to 5 languages, and
an authoring system for medical drug descriptions.
</P>
<P>
Later projects using GF and involving third parties include, in chronological order,
</P>
<UL>
<LI><A HREF="http://www.cs.chalmers.se/~hallgren/Alfa/Tutorial/GFplugin.html">GF-Alfa</A>:
natural language interface to formal proofs
<LI><A HREF="http://efficient.citi.tudor.lu/index_noframe.html">Efficient</A>:
authoring tool for business models.
<LI><A HREF="http://www.key-project.org/">GF-KeY</A>:
authoring and translation of software specifications
<LI><A HREF="http://www.talk-project.org">TALK</A>:
multilingual and multimodal spoken dialogue systems
<LI><A HREF="http://webalt.math.helsinki.fi/">WebALT</A>:
multilingual generation of mathematical exercises (commercial project)
<LI><A HREF="http://spraakbanken.gu.se/sal/">SALDO</A>:
Swedish morphological dictionary based on rules developed for GF and
<A HREF="http://www.cse.chalmers.se/alumni/markus/FM/">Functional Morphology</A>
<LI><a href="http://www.molto-project.eu">MOLTO</a>:
multilingual online translation
<LI><a href="http://remu.grammaticalframework.org">REMU</a>:
reliable multilingual digital communication.
</UL>
<p>
Here is a <a
href="http://videos.xrce.xerox.com/index.php/videos/index/618">talk
about GF at XRCE</a>,
14 years later.
<P>
Academically, GF has been used in at least ten PhD theses and resulted
in more than a hundred
scientific publications (see <A HREF="doc/gf-bibliography.html">GF publication list</A>).
</P>
<H2>Programming in GF</H2>
<P>
GF is easy to learn by following the <A HREF="doc/tutorial/gf-tutorial.html">tutorial</A>.
You can write your first translator in 15 minutes.
</P>
<P>
GF has an interactive command interpreter, as well as a batch compiler.
Grammars can be compiled to parser and translator code in many different
formats. These components can then be embedded in applications written
in other programming languages. The formats currently supported are:
</P>
<UL>
<LI>Haskell
<li>Java, in particular the Android platform
<LI>JavaScript
<LI>Speech recognition: HTK/ATK, Nuance, JSGF
</UL>
<P>
The GF programming language is high-level and advanced, featuring
</P>
<UL>
<LI>static type checking
<LI>higher-order functions
<LI>dependent types
<LI>pattern matching with data constructors and regular expressions
<LI>module system with multiple inheritance and parametrized modules
</UL>
<h3>Getting help</h3>
<p>
If you need some help with GF, the first places to start are the <a href="doc/tutorial/gf-tutorial.html">Tutorial</a> and <a href="doc/gf-refman.html">Reference</a> pages.
The printed <a href="gf-book">book</a> contains all the material in the tutorial and some extra bits, and is the recommended reference for GF.
</p>
<p>
We run the IRC channel <strong><code>#gf</code></strong> on the Freenode network, where you are welcome to look for help with small questions or just start a general discussion.
IRC logs (in raw format) are available <a href="irc/">here</a>.
If you have a larger question which the community may benefit from, we recommend you ask it on the <a href="http://groups.google.com/group/gf-dev">mailing list</a>.
</p>
<hr>
<H2>Libraries</H2>
<P>
Libraries are at the heart of modern software engineering. In natural language
applications, libraries are a way to cope with thousands of details involved in
syntax, lexicon, and inflection. The
<A HREF="lib/doc/synopsis.html">GF resource grammar library</A> has
support for an increasing number of languages, currently including
</P>
<ol class=languages>
<LI>Afrikaans
<LI>Amharic (partial)
<LI>Arabic (partial)
<LI>Bulgarian
<LI>Catalan
<LI>Chinese
<LI>Danish
<LI>Dutch
<LI>English
<LI>Estonian
<LI>Finnish
<LI>French
<LI>German
<li>Greek ancient (partial)
<li>Greek modern
<li>Hebrew (fragments)
<LI>Hindi
<LI><A HREF="http://www.interlingua.com/">Interlingua</A>
<LI>Japanese
<LI>Italian
<LI>Latin (fragments)
<LI>Latvian
<li>Maltese
<li>Mongolian
<LI>Nepali
<LI>Norwegian bokmål
<LI>Norwegian nynorsk
<LI>Persian
<LI>Polish
<li>Punjabi
<LI>Romanian
<LI>Russian
<LI>Sindhi
<LI>Slovene (partial)
<LI>Spanish
<li>Swahili (fragments)
<LI>Swedish
<LI>Thai
<LI>Turkish (fragments)
<LI>Urdu
</ol>
<div class="row">
<P>
Adding a language to the resource library takes 3 to 9
months - contributions
are welcome! You can start with the <A HREF="doc/gf-lrec-2010.pdf">resource grammarian's tutorial</A>.
<div class="col-md-6">
<h2>Applications & Availability</h2>
<p>
GF can be used for building
<a href="http://cloud.grammaticalframework.org/translator/">translation systems</a>,
<a href="http://cloud.grammaticalframework.org/minibar/minibar.html">multilingual web gadgets</a>,
<a href="http://www.cs.chalmers.se/~hallgren/Alfa/Tutorial/GFplugin.html">natural-language interfaces</a>,
<a href="http://www.youtube.com/watch?v=1bfaYHWS6zU">dialogue systems</a>, and
<a href="lib/doc/synopsis/index.html">natural language resources</a>.
</p>
<p>
GF is <strong>open-source</strong>, licensed under <a href="LICENSE">GPL</a> (the program) and
<a href="LICENSE">LGPL</a> and <a href="LICENSE">BSD</a> (the libraries). It
is available for
</p>
<ul>
<li>Linux</li>
<li>macOS</li>
<li>Windows</li>
<li>Android mobile platform (via Java; runtime)</li>
<li>via compilation to JavaScript, almost any platform that has a web browser (runtime)</li>
</ul>
<h2>Programming in GF</h2>
<p>
GF is easy to learn by following the <a href="doc/tutorial/gf-tutorial.html">tutorial</a>.
You can write your first translator in 15 minutes.
</p>
<p>
GF has an interactive command interpreter, as well as a batch compiler.
Grammars can be compiled to parser and translator code in many different
formats. These components can then be embedded in applications written
in other programming languages. The formats currently supported are:
</p>
<ul>
<li>Haskell</li>
<li>Java, in particular the Android platform</li>
<li>JavaScript</li>
<li>Speech recognition: HTK/ATK, Nuance, JSGF</li>
</ul>
<p>
The GF programming language is high-level and advanced, featuring:
</p>
<ul>
<li>static type checking</li>
<li>higher-order functions</li>
<li>dependent types</li>
<li>pattern matching with data constructors and regular expressions</li>
<li>module system with multiple inheritance and parametrized modules</li>
</ul>
<h3>Getting help</h3>
<p>
If you need some help with GF, the first places to start are the <a href="doc/tutorial/gf-tutorial.html">Tutorial</a> and <a href="doc/gf-refman.html">Reference</a> pages.
The printed <a href="gf-book">book</a> contains all the material in the tutorial and some extra bits, and is the recommended reference for GF.
</p>
<p>
We run the IRC channel <strong><code>#gf</code></strong> on the Freenode network, where you are welcome to look for help with small questions or just start a general discussion.
You can <a href="https://webchat.freenode.net/?channels=gf">open a web chat</a>
or <a href="http://www.grammaticalframework.org/irc/">browse the channel logs</a>.
</p>
<p>
If you have a larger question which the community may benefit from, we recommend you ask it on the <a href="http://groups.google.com/group/gf-dev">mailing list</a>.
</p>
</div>
<div class="col-md-6">
<h2>News</h2>
<dl class="row">
<dt class="col-sm-3 text-center text-nowrap">2018-12-03</dt>
<dd class="col-sm-9">
<a href="http://school.grammaticalframework.org/2018/">Sixth GF Summer School</a> in Stellenbosch (South Africa), 314 December 2018
</dd>
<dt class="col-sm-3 text-center text-nowrap">2018-12-02</dt>
<dd class="col-sm-9">
<strong>GF 3.10 released.</strong>
<a href="download/release-3.10.html">Release notes</a>
</dd>
<dt class="col-sm-3 text-center text-nowrap">2018-07-25</dt>
<dd class="col-sm-9">
The GF repository has been split in two:
<a href="https://github.com/GrammaticalFramework/gf-core">gf-core</a> and
<a href="https://github.com/GrammaticalFramework/gf-rgl">gf-rgl</a>.
The original <a href="https://github.com/GrammaticalFramework/GF">GF</a> repository is now archived.
</dd>
<dt class="col-sm-3 text-center text-nowrap">2017-08-11</dt>
<dd class="col-sm-9">
<strong>GF 3.9 released.</strong>
<a href="download/release-3.9.html">Release notes</a>
</dd>
<dt class="col-sm-3 text-center text-nowrap">2017-06-29</dt>
<dd class="col-sm-9">
GF is moving to <a href="https://github.com/GrammaticalFramework/GF/">GitHub</a>.</dd>
<dt class="col-sm-3 text-center text-nowrap">2017-03-13</dt>
<dd class="col-sm-9">
<a href="http://school.grammaticalframework.org/2017/">GF Summer School</a> in Riga (Latvia), 14-25 August 2017
</dd>
</dl>
<h2>Projects</h2>
<p>
GF was first created in 1998 at
<a href="http://www.xrce.xerox.com/">Xerox Research Centre Europe</a>,
Grenoble, in the project
Multilingual Document Authoring. At Xerox, it was used for prototypes including
a restaurant phrase book,
a database query system,
a formalization of an alarm system instructions with translations to 5 languages, and
an authoring system for medical drug descriptions.
</p>
<p>
Later projects using GF and involving third parties include, in chronological order:
</p>
<ul>
<li>
<a href="http://www.cs.chalmers.se/~hallgren/Alfa/Tutorial/GFplugin.html">GF-Alfa</a>:
natural language interface to formal proofs
</li>
<li>
<a href="http://efficient.citi.tudor.lu/index_noframe.html">Efficient</a>:
authoring tool for business models.
</li>
<li>
<a href="http://www.key-project.org/">GF-KeY</a>:
authoring and translation of software specifications
</li>
<li>
<a href="http://www.talk-project.org">TALK</a>:
multilingual and multimodal spoken dialogue systems
</li>
<li>
<a href="http://webalt.math.helsinki.fi/">WebALT</a>:
multilingual generation of mathematical exercises (commercial project)
</li>
<li>
<a href="http://spraakbanken.gu.se/sal/">SALDO</a>:
Swedish morphological dictionary based on rules developed for GF and
<a href="http://www.cse.chalmers.se/alumni/markus/FM/">Functional Morphology</a>
</li>
<li>
<a href="http://www.molto-project.eu">MOLTO</a>:
multilingual online translation
</li>
<li>
<a href="http://remu.grammaticalframework.org">REMU</a>:
reliable multilingual digital communication
</li>
</ul>
<!-- <p>
Here is a <a
href="http://videos.xrce.xerox.com/index.php/videos/index/618">talk
about GF at XRCE</a>,
14 years later.
</p> -->
<p>
Academically, GF has been used in at least ten PhD theses and resulted
in more than a hundred scientific publications.
<!-- (see <a href="doc/gf-bibliography.html">GF publication list</a>). -->
</p>
<h2>Libraries</h2>
<p>
Libraries are at the heart of modern software engineering. In natural language
applications, libraries are a way to cope with thousands of details involved in
syntax, lexicon, and inflection. The
<a href="lib/doc/synopsis/index.html">GF resource grammar library</a> has
support for an increasing number of languages, currently including
Afrikaans,
Amharic (partial),
Arabic (partial),
Bulgarian,
Catalan,
Chinese,
Danish,
Dutch,
English,
Estonian,
Finnish,
French,
German,
Greek ancient (partial),
Greek modern,
Hebrew (fragments),
Hindi,
Interlingua,
Japanese,
Italian,
Latin (fragments),
Latvian,
Maltese,
Mongolian,
Nepali,
Norwegian bokmål,
Norwegian nynorsk,
Persian,
Polish,
Punjabi,
Romanian,
Russian,
Sindhi,
Slovene (partial),
Spanish,
Swahili (fragments),
Swedish,
Thai,
Turkish (fragments),
and
Urdu.
</p>
<p>
Adding a language to the resource library takes 3 to 9
months - contributions
are welcome! You can start with the <a href="lib/doc/rgl-tutorial/index.html">resource grammarian's tutorial</a>.
</p>
</div><!-- .col-6 -->
</div><!-- .row -->
</div><!-- .container -->
<footer class="bg-light mt-5 py-4">
<div class="container mb-3">
<div class="text-center text-muted">
<img style="height:50px; filter: opacity(.5) grayscale(1);" class="mb-3" src="doc/Logos/gf0.svg" alt="GF Logo"><br>
Grammatical Framework is free and open source,<br>
with some support from <a href="https://www.digitalgrammars.com/">Digital Grammars AB</a>.
</div>
</div>
</footer>
<script type="text/javascript">
var gaJsHost = (("https:" == document.location.protocol) ? "https://ssl." : "http://www.");
@@ -423,5 +395,6 @@ try {
var pageTracker = _gat._getTracker("UA-7811807-3");
pageTracker._trackPageview();
} catch(err) {}</script>
</BODY>
</HTML>
</body>
</html>

View File

@@ -19,7 +19,9 @@ module GF(
module GF.Grammar.Printer,
module GF.Infra.Ident,
-- ** Binary serialisation
module GF.Grammar.Binary
module GF.Grammar.Binary,
-- * Canonical GF
module GF.Compile.GrammarToCanonical
) where
import GF.Main
import GF.Compiler
@@ -36,3 +38,5 @@ import GF.Grammar.Macros
import GF.Grammar.Printer
import GF.Infra.Ident
import GF.Grammar.Binary
import GF.Compile.GrammarToCanonical

View File

@@ -147,11 +147,17 @@ checkCompleteGrammar opts cwd gr (am,abs) (cm,cnc) = checkInModule cwd cnc NoLoc
return $ updateTree (c,CncFun (Just linty) d mn mf) js
_ -> do checkWarn ("function" <+> c <+> "is not in abstract")
return js
CncCat _ _ _ _ _ -> case lookupOrigInfo gr (am,c) of
Ok _ -> return $ updateTree i js
_ -> do checkWarn ("category" <+> c <+> "is not in abstract")
return js
_ -> return $ updateTree i js
CncCat {} ->
case lookupOrigInfo gr (am,c) of
Ok (_,AbsCat _) -> return $ updateTree i js
{- -- This might be too pedantic:
Ok (_,AbsFun {}) ->
checkError ("lincat:"<+>c<+>"is a fun, not a cat")
-}
_ -> do checkWarn ("category" <+> c <+> "is not in abstract")
return js
_ -> return $ updateTree i js
-- | General Principle: only Just-values are checked.

View File

@@ -1,365 +1,351 @@
-- | Translate concrete syntax to Haskell
module GF.Compile.ConcreteToHaskell(concretes2haskell,concrete2haskell) where
import Data.List(sort,sortBy)
import Data.Function(on)
import Data.List(isPrefixOf,sort,sortOn)
import qualified Data.Map as M
import qualified Data.Set as S
import GF.Data.ErrM
import GF.Data.Utilities(mapSnd)
import GF.Text.Pretty
import GF.Grammar.Grammar
import GF.Grammar.Lookup(lookupFunType,lookupOrigInfo,allOrigInfos)--,allParamValues
import GF.Grammar.Macros(typeForm,collectOp,collectPattOp,mkAbs,mkApp)
import GF.Grammar.Lockfield(isLockLabel)
import GF.Grammar.Predef(cPredef,cInts)
import GF.Compile.Compute.Predef(predef)
import GF.Compile.Compute.Value(Predefined(..))
import GF.Infra.Ident(Ident,identS,prefixIdent) --,moduleNameS
--import GF.Grammar.Predef(cPredef,cInts)
--import GF.Compile.Compute.Predef(predef)
--import GF.Compile.Compute.Value(Predefined(..))
import GF.Infra.Ident(Ident,identS,identW,prefixIdent)
import GF.Infra.Option
import GF.Compile.Compute.ConcreteNew(normalForm,resourceValues)
import GF.Haskell
import Debug.Trace
import GF.Haskell as H
import GF.Grammar.Canonical as C
import GF.Compile.GrammarToCanonical
import Debug.Trace(trace)
-- | Generate Haskell code for the all concrete syntaxes associated with
-- the named abstract syntax in given the grammar.
concretes2haskell opts absname gr =
[(cncname,concrete2haskell opts gr cenv absname cnc cncmod)
| let cenv = resourceValues opts gr,
cnc<-allConcretes gr absname,
let cncname = render cnc ++ ".hs" :: FilePath
Ok cncmod = lookupModule gr cnc
[(filename,render80 $ concrete2haskell opts abstr cncmod)
| let Grammar abstr cncs = grammar2canonical opts absname gr,
cncmod<-cncs,
let ModId name = concName cncmod
filename = name ++ ".hs" :: FilePath
]
-- | Generate Haskell code for the given concrete module.
-- The only options that make a difference are
-- @-haskell=noprefix@ and @-haskell=variants@.
concrete2haskell opts gr cenv absname cnc modinfo =
renderStyle style{lineLength=80,ribbonsPerLine=1} $
haskPreamble va absname cnc $$ vcat (
nl:Comment "--- Parameter types ---":
neededParamTypes S.empty (params defs) ++
nl:Comment "--- Type signatures for linearization functions ---":
map signature (S.toList allcats)++
nl:Comment "--- Linearization functions for empty categories ---":
emptydefs ++
nl:Comment "--- Linearization types and linearization functions ---":
map ppDef defs ++
nl:Comment "--- Type classes for projection functions ---":
map labelClass (S.toList labels) ++
nl:Comment "--- Record types ---":
concatMap recordType recs)
concrete2haskell opts
abstr@(Abstract _ _ cats funs)
modinfo@(Concrete cnc absname _ ps lcs lns) =
haskPreamble absname cnc $$
vcat (
nl:Comment "--- Parameter types ---":
map paramDef ps ++
nl:Comment "--- Type signatures for linearization functions ---":
map signature cats ++
nl:Comment "--- Linearization functions for empty categories ---":
emptydefs ++
nl:Comment "--- Linearization types ---":
map lincatDef lcs ++
nl:Comment "--- Linearization functions ---":
lindefs ++
nl:Comment "--- Type classes for projection functions ---":
map labelClass (S.toList labels) ++
nl:Comment "--- Record types ---":
concatMap recordType recs)
where
nl = Comment ""
recs = S.toList (S.difference (records (lcs,lns)) common_records)
labels = S.difference (S.unions (map S.fromList recs)) common_labels
recs = S.toList (S.difference (records rhss) common_records)
common_records = S.fromList [[label_s]]
common_labels = S.fromList [label_s]
label_s = ident2label (identS "s")
label_s = LabelId "s"
rhss = map (either snd (snd.snd)) defs
defs = sortBy (compare `on` either (const Nothing) (Just . fst)) .
concatMap (toHaskell gId gr absname cenv) .
M.toList $
jments modinfo
-- signature c = "lin"<>c<+>"::"<+>"A."<>gId c<+>"->"<+>"Lin"<>c
-- signature c = "--lin"<>c<+>":: (Applicative f,Monad f) =>"<+>"A."<>gId c<+>"->"<+>"f Lin"<>c
signature c = TypeSig lf (Fun abs (pure lin))
signature (CatDef c _) = TypeSig lf (Fun abs (pure lin))
where
abs = tcon0 (prefixIdent "A." (gId c))
lin = tcon0 lc
lf = prefixIdent "lin" c
lc = prefixIdent "Lin" c
lf = linfunName c
lc = lincatName c
emptydefs = map emptydef (S.toList emptyCats)
emptydef c = Eqn (prefixIdent "lin" c,[WildP]) (Const "undefined")
emptydef c = Eqn (linfunName c,[WildP]) (Const "undefined")
emptyCats = allcats `S.difference` cats
cats = S.fromList [c|Right (c,_)<-defs]
allcats = S.fromList [c|((_,c),AbsCat (Just _))<-allOrigInfos gr absname]
emptyCats = allcats `S.difference` linfuncats
where
--funcats = S.fromList [c | FunDef f (C.Type _ (TypeApp c _))<-funs]
allcats = S.fromList [c | CatDef c _<-cats]
gId :: ToIdent i => i -> Ident
gId = (if haskellOption opts HaskellNoPrefix then id else prefixIdent "G")
. toIdent
params = S.toList . S.unions . map params1
params1 (Left (_,rhs)) = paramTypes gr rhs
params1 (Right (_,(_,rhs))) = tableTypes gr [rhs]
ppDef (Left (lhs,rhs)) = lhs (convType va gId rhs)
ppDef (Right (_,(lhs,rhs))) = lhs (convert va gId gr rhs)
gId :: Ident -> Ident
gId = if haskellOption opts HaskellNoPrefix then id else prefixIdent "G"
va = haskellOption opts HaskellVariants
pure = if va then ListT else id
neededParamTypes have [] = []
neededParamTypes have (q:qs) =
if q `S.member` have
then neededParamTypes have qs
else let ((got,need),def) = paramType va gId gr q
in def++neededParamTypes (S.union got have) (S.toList need++qs)
haskPreamble :: Bool -> ModuleName -> ModuleName -> Doc
haskPreamble va absname cncname =
"{-# LANGUAGE MultiParamTypeClasses, FunctionalDependencies, FlexibleInstances, LambdaCase #-}" $$
"module" <+> cncname <+> "where" $$
"import Prelude hiding (Ordering(..))" $$
"import Control.Applicative((<$>),(<*>))" $$
"import PGF.Haskell" $$
"import qualified" <+> absname <+> "as A" $$
"" $$
"--- Standard definitions ---" $$
"linString (A.GString s) ="<+>pure "R_s [TK s]" $$
"linInt (A.GInt i) ="<+>pure "R_s [TK (show i)]" $$
"linFloat (A.GFloat x) ="<+>pure "R_s [TK (show x)]" $$
"" $$
"----------------------------------------------------" $$
"-- Automatic translation from GF to Haskell follows" $$
"----------------------------------------------------"
where
pure = if va then brackets else pp
toHaskell gId gr absname cenv (name,jment) =
case jment of
CncCat (Just (L loc typ)) _ _ pprn _ ->
[Left (tsyn0 (prefixIdent "Lin" name),nf loc typ)]
CncFun (Just r@(cat,ctx,lincat)) (Just (L loc def)) pprn _ ->
-- trace (render (name<+>hcat[parens (x<>"::"<>t)|(_,x,t)<-ctx]<+>"::"<+>cat)) $
[Right (cat,(Eqn (prefixIdent "lin" cat,lhs),coerce [] lincat rhs))]
haskPreamble :: ModId -> ModId -> Doc
haskPreamble absname cncname =
"{-# LANGUAGE MultiParamTypeClasses, FunctionalDependencies, FlexibleInstances, LambdaCase #-}" $$
"module" <+> cncname <+> "where" $$
"import Prelude hiding (Ordering(..))" $$
"import Control.Applicative((<$>),(<*>))" $$
"import PGF.Haskell" $$
"import qualified" <+> absname <+> "as A" $$
"" $$
"--- Standard definitions ---" $$
"linString (A.GString s) ="<+>pure "R_s [TK s]" $$
"linInt (A.GInt i) ="<+>pure "R_s [TK (show i)]" $$
"linFloat (A.GFloat x) ="<+>pure "R_s [TK (show x)]" $$
"" $$
"----------------------------------------------------" $$
"-- Automatic translation from GF to Haskell follows" $$
"----------------------------------------------------"
where
Ok abstype = lookupFunType gr absname name
(absctx,_abscat,_absargs) = typeForm abstype
pure = if va then brackets else pp
e' = unAbs (length params) $
nf loc (mkAbs params (mkApp def (map Vr args)))
params = [(b,prefixIdent "g" x)|(b,x,_)<-ctx]
args = map snd params
abs_args = map (prefixIdent "abs_") args
lhs = [ConP (aId name) (map VarP abs_args)]
rhs = foldr letlin e' (zip args absctx)
letlin (a,(_,_,at)) =
Let (a,(Just (con ("Lin"++render at)),(App (con ("lin"++render at)) (con ("abs_"++render a)))))
AnyInd _ m -> case lookupOrigInfo gr (m,name) of
Ok (m,jment) -> toHaskell gId gr absname cenv (name,jment)
_ -> []
_ -> []
where
nf loc = normalForm cenv (L loc name)
aId n = prefixIdent "A." (gId n)
paramDef pd =
case pd of
ParamAliasDef p t -> H.Type (conap0 (gId p)) (convLinType t)
ParamDef p pvs -> Data (conap0 (gId p)) (map paramCon pvs) derive
where
paramCon (Param c cs) = ConAp (gId c) (map (tcon0.gId) cs)
derive = ["Eq","Ord","Show"]
unAbs 0 t = t
unAbs n (Abs _ _ t) = unAbs (n-1) t
unAbs _ t = t
convLinType = ppT
where
ppT t =
case t of
FloatType -> tcon0 (identS "Float")
IntType -> tcon0 (identS "Int")
ParamType (ParamTypeId p) -> tcon0 (gId p)
RecordType rs -> tcon (rcon' ls) (map ppT ts)
where (ls,ts) = unzip $ sortOn fst [(l,t)|RecordRow l t<-rs]
StrType -> tcon0 (identS "Str")
TableType pt lt -> Fun (ppT pt) (ppT lt)
-- TupleType lts ->
lincatDef (LincatDef c t) = tsyn0 (lincatName c) (convLinType t)
linfuncats = S.fromList linfuncatl
(linfuncatl,lindefs) = unzip (linDefs lns)
linDefs = map eqn . sortOn fst . map linDef
where eqn (cat,(f,(ps,rhs))) = (cat,Eqn (f,ps) rhs)
linDef (LinDef f xs rhs0) =
(cat,(linfunName cat,(lhs,rhs)))
where
lhs = [ConP (aId f) (map VarP abs_args)]
aId f = prefixIdent "A." (gId f)
[lincat] = [lincat | LincatDef c lincat<-lcs,c==cat]
[C.Type absctx (TypeApp cat _)] = [t | FunDef f' t<-funs, f'==f]
abs_args = map abs_arg args
abs_arg = prefixIdent "abs_"
args = map (prefixIdent "g" . toIdent) xs
rhs = lets (zipWith letlin args absctx)
(convert vs (coerce env lincat rhs0))
where
vs = [(VarValueId (Unqual x),a)|(VarId x,a)<-zip xs args]
env= [(VarValueId (Unqual x),lc)|(VarId x,lc)<-zip xs (map arglincat absctx)]
letlin a (TypeBinding _ (C.Type _ (TypeApp acat _))) =
(a,Ap (Var (linfunName acat)) (Var (abs_arg a)))
arglincat (TypeBinding _ (C.Type _ (TypeApp acat _))) = lincat
where
[lincat] = [lincat | LincatDef c lincat<-lcs,c==acat]
convert = convert' va
convert' va vs = ppT
where
ppT0 = convert' False vs
ppTv vs' = convert' va vs'
pure = if va then single else id
ppT t =
case t of
TableValue ty cs -> pure (table cs)
Selection t p -> select (ppT t) (ppT p)
ConcatValue t1 t2 -> concat (ppT t1) (ppT t2)
RecordValue r -> aps (rcon ls) (map ppT ts)
where (ls,ts) = unzip $ sortOn fst [(l,t)|RecordRow l t<-r]
PredefValue p -> single (Var (toIdent p)) -- hmm
Projection t l -> ap (proj l) (ppT t)
VariantValue [] -> empty
VariantValue ts@(_:_) -> variants ts
VarValue x -> maybe (Var (gId x)) (pure . Var) $ lookup x vs
PreValue vs t' -> pure (alts t' vs)
ParamConstant (Param c vs) -> aps (Var (pId c)) (map ppT vs)
ErrorValue s -> ap (Const "error") (Const (show s)) -- !!
LiteralValue l -> ppL l
_ -> error ("convert "++show t)
ppL l =
case l of
FloatConstant x -> pure (lit x)
IntConstant n -> pure (lit n)
StrConstant s -> pure (token s)
pId p@(ParamId s) =
if "to_R_" `isPrefixOf` unqual s then toIdent p else gId p -- !! a hack
table cs =
if all (null.patVars) ps
then lets ds (LambdaCase [(ppP p,t')|(p,t')<-zip ps ts'])
else LambdaCase (map ppCase cs)
where
(ds,ts') = dedup ts
(ps,ts) = unzip [(p,t)|TableRow p t<-cs]
ppCase (TableRow p t) = (ppP p,ppTv (patVars p++vs) t)
{-
ppPredef n =
case predef n of
Ok BIND -> single (c "BIND")
Ok SOFT_BIND -> single (c "SOFT_BIND")
Ok SOFT_SPACE -> single (c "SOFT_SPACE")
Ok CAPIT -> single (c "CAPIT")
Ok ALL_CAPIT -> single (c "ALL_CAPIT")
_ -> Var n
-}
ppP p =
case p of
ParamPattern (Param c ps) -> ConP (gId c) (map ppP ps)
RecordPattern r -> ConP (rcon' ls) (map ppP ps)
where (ls,ps) = unzip $ sortOn fst [(l,p)|RecordRow l p<-r]
WildPattern -> WildP
token s = single (c "TK" `Ap` lit s)
alts t' vs = single (c "TP" `Ap` List (map alt vs) `Ap` ppT0 t')
where
alt (s,t) = Pair (List (pre s)) (ppT0 t)
pre s = map lit s
c = Const
lit s = c (show s) -- hmm
concat = if va then concat' else plusplus
where
concat' (List [List ts1]) (List [List ts2]) = List [List (ts1++ts2)]
concat' t1 t2 = Op t1 "+++" t2
pure' = single -- forcing the list monad
select = if va then select' else Ap
select' (List [t]) (List [p]) = Op t "!" p
select' (List [t]) p = Op t "!$" p
select' t p = Op t "!*" p
ap = if va then ap' else Ap
where
ap' (List [f]) x = fmap f x
ap' f x = Op f "<*>" x
fmap f (List [x]) = pure' (Ap f x)
fmap f x = Op f "<$>" x
-- join = if va then join' else id
join' (List [x]) = x
join' x = c "concat" `Ap` x
empty = if va then List [] else c "error" `Ap` c (show "empty variant")
variants = if va then \ ts -> join' (List (map ppT ts))
else \ (t:_) -> ppT t
aps f [] = f
aps f (a:as) = aps (ap f a) as
dedup ts =
if M.null dups
then ([],map ppT ts)
else ([(ev i,ppT t)|(i,t)<-defs],zipWith entry ts is)
where
entry t i = maybe (ppT t) (Var . ev) (M.lookup i dups)
ev i = identS ("e'"++show i)
defs = [(i1,t)|(t,i1:_:_)<-ms]
dups = M.fromList [(i2,i1)|(_,i1:is@(_:_))<-ms,i2<-i1:is]
ms = M.toList m
m = fmap sort (M.fromListWith (++) (zip ts [[i]|i<-is]))
is = [0..]::[Int]
con = Cn . identS
--con = Cn . identS
tableTypes gr ts = S.unions (map tabtys ts)
where
tabtys t =
case t of
V t cc -> S.union (paramTypes gr t) (tableTypes gr cc)
T (TTyped t) cs -> S.union (paramTypes gr t) (tableTypes gr (map snd cs))
_ -> collectOp tabtys t
class Records t where
records :: t -> S.Set [LabelId]
paramTypes gr t =
case t of
RecType fs -> S.unions (map (paramTypes gr.snd) fs)
Table t1 t2 -> S.union (paramTypes gr t1) (paramTypes gr t2)
App tf ta -> S.union (paramTypes gr tf) (paramTypes gr ta)
Sort _ -> S.empty
EInt _ -> S.empty
Q q -> lookup q
QC q -> lookup q
FV ts -> S.unions (map (paramTypes gr) ts)
_ -> ignore
where
lookup q = case lookupOrigInfo gr q of
Ok (_,ResOper _ (Just (L _ t))) ->
S.insert q (paramTypes gr t)
Ok (_,ResParam {}) -> S.singleton q
_ -> ignore
instance Records t => Records [t] where
records = S.unions . map records
ignore = trace ("Ignore: "++show t) S.empty
records ts = S.unions (map recs ts)
where
recs t =
case t of
R r -> S.insert (labels r) (records (map (snd.snd) r))
RecType r -> S.insert (labels r) (records (map snd r))
_ -> collectOp recs t
labels = sort . filter (not . isLockLabel) . map fst
instance (Records t1,Records t2) => Records (t1,t2) where
records (t1,t2) = S.union (records t1) (records t2)
instance Records LincatDef where
records (LincatDef _ lt) = records lt
instance Records LinDef where
records (LinDef _ _ lv) = records lv
instance Records LinType where
records t =
case t of
RecordType r -> rowRecords r
TableType pt lt -> records (pt,lt)
TupleType ts -> records ts
_ -> S.empty
rowRecords r = S.insert (sort ls) (records ts)
where (ls,ts) = unzip [(l,t)|RecordRow l t<-r]
instance Records LinValue where
records v =
case v of
ConcatValue v1 v2 -> records (v1,v2)
ParamConstant (Param c vs) -> records vs
RecordValue r -> rowRecords r
TableValue t r -> records (t,r)
TupleValue vs -> records vs
VariantValue vs -> records vs
PreValue alts d -> records (map snd alts,d)
Projection v l -> records v
Selection v1 v2 -> records (v1,v2)
_ -> S.empty
instance Records rhs => Records (TableRow rhs) where
records (TableRow _ v) = records v
-- | Record subtyping is converted into explicit coercions in Haskell
coerce env ty t =
case (ty,t) of
(_,Let d t) -> Let d (coerce (extend env d) ty t)
(_,FV ts) -> FV (map (coerce env ty) ts)
(Table ti tv,V _ ts) -> V ti (map (coerce env tv) ts)
(Table ti tv,T (TTyped _) cs) -> T (TTyped ti) (mapSnd (coerce env tv) cs)
(RecType rt,R r) ->
R [(l,(Just ft,coerce env ft f))|(l,(_,f))<-r,Just ft<-[lookup l rt]]
(RecType rt,Vr x)->
(_,VariantValue ts) -> VariantValue (map (coerce env ty) ts)
(TableType ti tv,TableValue _ cs) ->
TableValue ti [TableRow p (coerce env tv t)|TableRow p t<-cs]
(RecordType rt,RecordValue r) ->
RecordValue [RecordRow l (coerce env ft f) |
RecordRow l f<-r,ft<-[ft|RecordRow l' ft<-rt,l'==l]]
(RecordType rt,VarValue x)->
case lookup x env of
Just ty' | ty'/=ty -> -- better to compare to normal form of ty'
--trace ("coerce "++render ty'++" to "++render ty) $
App (to_rcon (map fst rt)) t
_ -> trace ("no coerce to "++render ty) t
--trace ("coerce "++render ty'++" to "++render ty) $
app (to_rcon rt) [t]
| otherwise -> t -- types match, no coercion needed
_ -> trace (render ("missing type to coerce"<+>x<+>"to"<+>render ty
$$ "in" <+> map fst env))
t
_ -> t
where
extend env (x,(Just ty,rhs)) = (x,ty):env
extend env _ = env
app f ts = ParamConstant (Param f ts) -- !! a hack
to_rcon = ParamId . Unqual . to_rcon' . labels
convert va gId gr = convert' va gId [] gr
patVars p = []
convert' va gId vs gr = ppT
where
ppT0 = convert' False gId vs gr
ppTv vs' = convert' va gId vs' gr
labels r = [l|RecordRow l _<-r]
ppT t =
case t of
-- Only for 'let' inserted on the top-level by this converter:
Let (x,(_,xt)) t -> let1 x (ppT0 xt) (ppT t)
-- Abs b x t -> ...
V ty ts -> pure (c "table" `Ap` dedup ts)
T (TTyped ty) cs -> pure (LambdaCase (map ppCase cs))
S t p -> select (ppT t) (ppT p)
C t1 t2 -> concat (ppT t1) (ppT t2)
App f a -> ap (ppT f) (ppT a)
R r -> aps (ppT (rcon (map fst r))) (fields r)
P t l -> ap (ppT (proj l)) (ppT t)
FV [] -> empty
Vr x -> if x `elem` vs then pure (Var x) else Var x
Cn x -> pure (Var x)
Con c -> pure (Var (gId c))
Sort k -> pure (Var k)
EInt n -> pure (lit n)
Q (m,n) -> if m==cPredef then pure (ppPredef n) else Var (qual m n)
QC (m,n) -> pure (Var (gId (qual m n)))
K s -> pure (token s)
Empty -> pure (List [])
FV ts@(_:_) -> variants ts
Alts t' vs -> pure (alts t' vs)
ppCase (p,t) = (ppP p,ppTv (patVars p++vs) t)
ppPredef n =
case predef n of
Ok BIND -> single (c "BIND")
Ok SOFT_BIND -> single (c "SOFT_BIND")
Ok SOFT_SPACE -> single (c "SOFT_SPACE")
Ok CAPIT -> single (c "CAPIT")
Ok ALL_CAPIT -> single (c "ALL_CAPIT")
_ -> Var n
ppP p =
case p of
PC c ps -> ConP (gId c) (map ppP ps)
PP (_,c) ps -> ConP (gId c) (map ppP ps)
PR r -> ConP (rcon' (map fst r)) (map (ppP.snd) (filter (not.isLockLabel.fst) r))
PW -> WildP
PV x -> VarP x
PString s -> Lit (show s) -- !!
PInt i -> Lit (show i)
PFloat x -> Lit (show x)
PT _ p -> ppP p
PAs x p -> AsP x (ppP p)
token s = single (c "TK" `Ap` lit s)
alts t' vs = single (c "TP" `Ap` List (map alt vs) `Ap` ppT0 t')
where
alt (t,p) = Pair (List (pre p)) (ppT0 t)
pre (K s) = [lit s]
pre (Strs ts) = concatMap pre ts
pre (EPatt p) = pat p
pre t = error $ "pre "++show t
pat (PString s) = [lit s]
pat (PAlt p1 p2) = pat p1++pat p2
pat p = error $ "pat "++show p
fields = map (ppT.snd.snd) . sort . filter (not.isLockLabel.fst)
c = Const
lit s = c (show s) -- hmm
concat = if va then concat' else plusplus
where
concat' (List [List ts1]) (List [List ts2]) = List [List (ts1++ts2)]
concat' t1 t2 = Op t1 "+++" t2
pure = if va then single else id
pure' = single -- forcing the list monad
select = if va then select' else Ap
select' (List [t]) (List [p]) = Op t "!" p
select' (List [t]) p = Op t "!$" p
select' t p = Op t "!*" p
ap = if va then ap' else Ap
where
ap' (List [f]) x = fmap f x
ap' f x = Op f "<*>" x
fmap f (List [x]) = pure' (Ap f x)
fmap f x = Op f "<$>" x
-- join = if va then join' else id
join' (List [x]) = x
join' x = c "concat" `Ap` x
empty = if va then List [] else c "error" `Ap` c (show "empty variant")
variants = if va then \ ts -> join' (List (map ppT ts))
else \ (t:_) -> ppT t
aps f [] = f
aps f (a:as) = aps (ap f a) as
dedup ts =
if M.null dups
then List (map ppT ts)
else Lets [(ev i,ppT t)|(i,t)<-defs] (List (zipWith entry ts is))
where
entry t i = maybe (ppT t) (Var . ev) (M.lookup i dups)
ev i = identS ("e'"++show i)
defs = [(i1,t)|(t,i1:_:_)<-ms]
dups = M.fromList [(i2,i1)|(_,i1:is@(_:_))<-ms,i2<-i1:is]
ms = M.toList m
m = fmap sort (M.fromListWith (++) (zip ts [[i]|i<-is]))
is = [0..]::[Int]
patVars p =
case p of
PV x -> [x]
PAs x p -> x:patVars p
_ -> collectPattOp patVars p
convType va gId = ppT
where
ppT t =
case t of
Table ti tv -> Fun (ppT ti) (if va then ListT (ppT tv) else ppT tv)
RecType rt -> tcon (rcon' (map fst rt)) (fields rt)
App tf ta -> TAp (ppT tf) (ppT ta)
FV [] -> tcon0 (identS "({-empty variant-})")
Sort k -> tcon0 k
EInt n -> tcon0 (identS ("({-"++show n++"-})")) -- type level numeric literal
FV (t:ts) -> ppT t -- !!
QC (m,n) -> tcon0 (gId (qual m n))
Q (m,n) -> tcon0 (gId (qual m n))
_ -> error $ "Missing case in convType for: "++show t
fields = map (ppT.snd) . sort . filter (not.isLockLabel.fst)
proj = con . proj'
proj' l = "proj_"++render l
rcon = con . rcon_name
proj = Var . identS . proj'
proj' (LabelId l) = "proj_"++l
rcon = Var . rcon'
rcon' = identS . rcon_name
rcon_name ls = "R"++concat (sort ['_':render l|l<-ls,not (isLockLabel l)])
to_rcon = con . to_rcon'
rcon_name ls = "R"++concat (sort ['_':l|LabelId l<-ls])
to_rcon' = ("to_"++) . rcon_name
recordType ls =
@@ -400,31 +386,6 @@ labelClass l =
r = identS "r"
a = identS "a"
paramType va gId gr q@(_,n) =
case lookupOrigInfo gr q of
Ok (m,ResParam (Just (L _ ps)) _)
{- - | m/=cPredef && m/=moduleNameS "Prelude"-} ->
((S.singleton (m,n),argTypes ps),
[Data (conap0 name) (map (param m) ps)["Eq","Ord","Show"],
Instance [] (TId (identS "EnumAll") `TAp` TId name)
[(lhs0 "enumAll",foldr1 plusplus (map (enumParam m) ps))]]
)
where name = gId (qual m n)
Ok (m,ResOper _ (Just (L _ t)))
| m==cPredef && n==cInts ->
((S.singleton (m,n),S.empty),
[Type (ConAp (gId (qual m n)) [identS "n"]) (TId (identS "Int"))])
| otherwise ->
((S.singleton (m,n),paramTypes gr t),
[Type (conap0 (gId (qual m n))) (convType va gId t)])
_ -> ((S.empty,S.empty),[])
where
param m (n,ctx) = ConAp (gId (qual m n)) [convType va gId t|(_,_,t)<-ctx]
argTypes = S.unions . map argTypes1
argTypes1 (n,ctx) = S.unions [paramTypes gr t|(_,_,t)<-ctx]
enumParam m (n,ctx) = enumCon (gId (qual m n)) (length ctx)
enumCon name arity =
if arity==0
then single (Var name)
@@ -433,5 +394,23 @@ enumCon name arity =
ap (List [f]) a = Op f "<$>" a
ap f a = Op f "<*>" a
qual :: ModuleName -> Ident -> Ident
qual m = prefixIdent (render m++"_")
lincatName,linfunName :: CatId -> Ident
lincatName c = prefixIdent "Lin" (toIdent c)
linfunName c = prefixIdent "lin" (toIdent c)
class ToIdent i where toIdent :: i -> Ident
instance ToIdent ParamId where toIdent (ParamId q) = qIdentS q
instance ToIdent PredefId where toIdent (PredefId s) = identS s
instance ToIdent CatId where toIdent (CatId s) = identS s
instance ToIdent C.FunId where toIdent (FunId s) = identS s
instance ToIdent VarValueId where toIdent (VarValueId q) = qIdentS q
qIdentS = identS . unqual
unqual (Qual (ModId m) n) = m++"_"++n
unqual (Unqual n) = n
instance ToIdent VarId where
toIdent Anonymous = identW
toIdent (VarId s) = identS s

View File

@@ -3,9 +3,11 @@ module GF.Compile.Export where
import PGF
import PGF.Internal(ppPGF)
import GF.Compile.PGFtoHaskell
--import GF.Compile.PGFtoAbstract
import GF.Compile.PGFtoJava
import GF.Compile.PGFtoProlog
import GF.Compile.PGFtoJS
import GF.Compile.PGFtoJSON
import GF.Compile.PGFtoPython
import GF.Infra.Option
--import GF.Speech.CFG
@@ -34,7 +36,10 @@ exportPGF :: Options
exportPGF opts fmt pgf =
case fmt of
FmtPGFPretty -> multi "txt" (render . ppPGF)
FmtCanonicalGF -> [] -- canon "gf" (render80 . abstract2canonical)
FmtCanonicalJson-> []
FmtJavaScript -> multi "js" pgf2js
FmtJSON -> multi "json" pgf2json
FmtPython -> multi "py" pgf2python
FmtHaskell -> multi "hs" (grammar2haskell opts name)
FmtJava -> multi "java" (grammar2java opts name)
@@ -57,9 +62,12 @@ exportPGF opts fmt pgf =
multi :: String -> (PGF -> String) -> [(FilePath,String)]
multi ext pr = [(name <.> ext, pr pgf)]
-- canon ext pr = [("canonical"</>name<.>ext,pr pgf)]
single :: String -> (PGF -> CId -> String) -> [(FilePath,String)]
single ext pr = [(showCId cnc <.> ext, pr pgf cnc) | cnc <- languages pgf]
-- | Get the name of the concrete syntax to generate output from.
-- FIXME: there should be an option to change this.
outputConcr :: PGF -> CId

View File

@@ -0,0 +1,388 @@
-- | Translate grammars to Canonical form
-- (a common intermediate representation to simplify export to other formats)
module GF.Compile.GrammarToCanonical(
grammar2canonical,abstract2canonical,concretes2canonical,
projection,selection
) where
import Data.List(nub,partition)
import qualified Data.Map as M
import qualified Data.Set as S
import GF.Data.ErrM
import GF.Text.Pretty
import GF.Grammar.Grammar
import GF.Grammar.Lookup(lookupOrigInfo,allOrigInfos,allParamValues)
import GF.Grammar.Macros(typeForm,collectOp,collectPattOp,mkAbs,mkApp,term2patt)
import GF.Grammar.Lockfield(isLockLabel)
import GF.Grammar.Predef(cPredef,cInts)
import GF.Compile.Compute.Predef(predef)
import GF.Compile.Compute.Value(Predefined(..))
import GF.Infra.Ident(ModuleName(..),Ident,prefixIdent,showIdent,isWildIdent)
import GF.Infra.Option(optionsPGF)
import PGF.Internal(Literal(..))
import GF.Compile.Compute.ConcreteNew(normalForm,resourceValues)
import GF.Grammar.Canonical as C
import Debug.Trace
-- | Generate Canonical code for the named abstract syntax and all associated
-- concrete syntaxes
grammar2canonical opts absname gr =
Grammar (abstract2canonical absname gr)
(map snd (concretes2canonical opts absname gr))
-- | Generate Canonical code for the named abstract syntax
abstract2canonical absname gr =
Abstract (modId absname) (convFlags gr absname) cats funs
where
cats = [CatDef (gId c) (convCtx ctx) | ((_,c),AbsCat ctx) <- adefs]
funs = [FunDef (gId f) (convType ty) |
((_,f),AbsFun (Just (L _ ty)) ma mdef _) <- adefs]
adefs = allOrigInfos gr absname
convCtx = maybe [] (map convHypo . unLoc)
convHypo (bt,name,t) =
case typeForm t of
([],(_,cat),[]) -> gId cat -- !!
convType t =
case typeForm t of
(hyps,(_,cat),args) -> Type bs (TypeApp (gId cat) as)
where
bs = map convHypo' hyps
as = map convType args
convHypo' (bt,name,t) = TypeBinding (gId name) (convType t)
-- | Generate Canonical code for the all concrete syntaxes associated with
-- the named abstract syntax in given the grammar.
concretes2canonical opts absname gr =
[(cncname,concrete2canonical gr cenv absname cnc cncmod)
| let cenv = resourceValues opts gr,
cnc<-allConcretes gr absname,
let cncname = "canonical/"++render cnc ++ ".gf" :: FilePath
Ok cncmod = lookupModule gr cnc
]
-- | Generate Canonical GF for the given concrete module.
concrete2canonical gr cenv absname cnc modinfo =
Concrete (modId cnc) (modId absname) (convFlags gr cnc)
(neededParamTypes S.empty (params defs))
[lincat|(_,Left lincat)<-defs]
[lin|(_,Right lin)<-defs]
where
defs = concatMap (toCanonical gr absname cenv) .
M.toList $
jments modinfo
params = S.toList . S.unions . map fst
neededParamTypes have [] = []
neededParamTypes have (q:qs) =
if q `S.member` have
then neededParamTypes have qs
else let ((got,need),def) = paramType gr q
in def++neededParamTypes (S.union got have) (S.toList need++qs)
toCanonical gr absname cenv (name,jment) =
case jment of
CncCat (Just (L loc typ)) _ _ pprn _ ->
[(pts,Left (LincatDef (gId name) (convType ntyp)))]
where
pts = paramTypes gr ntyp
ntyp = nf loc typ
CncFun (Just r@(cat,ctx,lincat)) (Just (L loc def)) pprn _ ->
[(tts,Right (LinDef (gId name) (map gId args) (convert gr e')))]
where
tts = tableTypes gr [e']
e' = unAbs (length params) $
nf loc (mkAbs params (mkApp def (map Vr args)))
params = [(b,x)|(b,x,_)<-ctx]
args = map snd params
AnyInd _ m -> case lookupOrigInfo gr (m,name) of
Ok (m,jment) -> toCanonical gr absname cenv (name,jment)
_ -> []
_ -> []
where
nf loc = normalForm cenv (L loc name)
-- aId n = prefixIdent "A." (gId n)
unAbs 0 t = t
unAbs n (Abs _ _ t) = unAbs (n-1) t
unAbs _ t = t
tableTypes gr ts = S.unions (map tabtys ts)
where
tabtys t =
case t of
V t cc -> S.union (paramTypes gr t) (tableTypes gr cc)
T (TTyped t) cs -> S.union (paramTypes gr t) (tableTypes gr (map snd cs))
_ -> collectOp tabtys t
paramTypes gr t =
case t of
RecType fs -> S.unions (map (paramTypes gr.snd) fs)
Table t1 t2 -> S.union (paramTypes gr t1) (paramTypes gr t2)
App tf ta -> S.union (paramTypes gr tf) (paramTypes gr ta)
Sort _ -> S.empty
EInt _ -> S.empty
Q q -> lookup q
QC q -> lookup q
FV ts -> S.unions (map (paramTypes gr) ts)
_ -> ignore
where
lookup q = case lookupOrigInfo gr q of
Ok (_,ResOper _ (Just (L _ t))) ->
S.insert q (paramTypes gr t)
Ok (_,ResParam {}) -> S.singleton q
_ -> ignore
ignore = trace ("Ignore: "++show t) S.empty
convert gr = convert' gr []
convert' gr vs = ppT
where
ppT0 = convert' gr vs
ppTv vs' = convert' gr vs'
ppT t =
case t of
-- Abs b x t -> ...
-- V ty ts -> VTableValue (convType ty) (map ppT ts)
V ty ts -> TableValue (convType ty) [TableRow (ppP p) (ppT t)|(p,t)<-zip ps ts]
where
Ok pts = allParamValues gr ty
Ok ps = mapM term2patt pts
T (TTyped ty) cs -> TableValue (convType ty) (map ppCase cs)
S t p -> selection (ppT t) (ppT p)
C t1 t2 -> concatValue (ppT t1) (ppT t2)
App f a -> ap (ppT f) (ppT a)
R r -> RecordValue (fields r)
P t l -> projection (ppT t) (lblId l)
Vr x -> VarValue (gId x)
Cn x -> VarValue (gId x) -- hmm
Con c -> ParamConstant (Param (gId c) [])
Sort k -> VarValue (gId k)
EInt n -> LiteralValue (IntConstant n)
Q (m,n) -> if m==cPredef then ppPredef n else VarValue ((gQId m n))
QC (m,n) -> ParamConstant (Param ((gQId m n)) [])
K s -> LiteralValue (StrConstant s)
Empty -> LiteralValue (StrConstant "")
FV ts -> VariantValue (map ppT ts)
Alts t' vs -> alts vs (ppT t')
_ -> error $ "convert' "++show t
ppCase (p,t) = TableRow (ppP p) (ppTv (patVars p++vs) t)
ppPredef n =
case predef n of
Ok BIND -> p "BIND"
Ok SOFT_BIND -> p "SOFT_BIND"
Ok SOFT_SPACE -> p "SOFT_SPACE"
Ok CAPIT -> p "CAPIT"
Ok ALL_CAPIT -> p "ALL_CAPIT"
_ -> VarValue (gQId cPredef n) -- hmm
where
p = PredefValue . PredefId
ppP p =
case p of
PC c ps -> ParamPattern (Param (gId c) (map ppP ps))
PP (m,c) ps -> ParamPattern (Param ((gQId m c)) (map ppP ps))
PR r -> RecordPattern (fields r) {-
PW -> WildPattern
PV x -> VarP x
PString s -> Lit (show s) -- !!
PInt i -> Lit (show i)
PFloat x -> Lit (show x)
PT _ p -> ppP p
PAs x p -> AsP x (ppP p) -}
where
fields = map field . filter (not.isLockLabel.fst)
field (l,p) = RecordRow (lblId l) (ppP p)
-- patToParam p = case ppP p of ParamPattern pv -> pv
-- token s = single (c "TK" `Ap` lit s)
alts vs = PreValue (map alt vs)
where
alt (t,p) = (pre p,ppT0 t)
pre (K s) = [s]
pre (Strs ts) = concatMap pre ts
pre (EPatt p) = pat p
pre t = error $ "pre "++show t
pat (PString s) = [s]
pat (PAlt p1 p2) = pat p1++pat p2
pat (PSeq p1 p2) = [s1++s2 | s1<-pat p1, s2<-pat p2]
pat p = error $ "pat "++show p
fields = map field . filter (not.isLockLabel.fst)
field (l,(_,t)) = RecordRow (lblId l) (ppT t)
--c = Const
--c = VarValue . VarValueId
--lit s = c (show s) -- hmm
ap f a = case f of
ParamConstant (Param p ps) ->
ParamConstant (Param p (ps++[a]))
_ -> error $ "convert' ap: "++render (ppA f <+> ppA a)
concatValue v1 v2 =
case (v1,v2) of
(LiteralValue (StrConstant ""),_) -> v2
(_,LiteralValue (StrConstant "")) -> v1
_ -> ConcatValue v1 v2
-- | Smart constructor for projections
projection r l = maybe (Projection r l) id (proj r l)
proj r l =
case r of
RecordValue r -> case [v|RecordRow l' v<-r,l'==l] of
[v] -> Just v
_ -> Nothing
_ -> Nothing
-- | Smart constructor for selections
selection t v =
-- Note: impossible cases can become possible after grammar transformation
case t of
TableValue tt r ->
case nub [rv|TableRow _ rv<-keep] of
[rv] -> rv
_ -> Selection (TableValue tt r') v
where
-- Don't introduce wildcard patterns, true to the canonical format,
-- annotate (or eliminate) rhs in impossible rows
r' = map trunc r
trunc r@(TableRow p e) = if mightMatchRow v r
then r
else TableRow p (impossible e)
{-
-- Creates smaller tables, but introduces wildcard patterns
r' = if null discard
then r
else keep++[TableRow WildPattern impossible]
-}
(keep,discard) = partition (mightMatchRow v) r
_ -> Selection t v
impossible = CommentedValue "impossible"
mightMatchRow v (TableRow p _) =
case p of
WildPattern -> True
_ -> mightMatch v p
mightMatch v p =
case v of
ConcatValue _ _ -> False
ParamConstant (Param c1 pvs) ->
case p of
ParamPattern (Param c2 pps) -> c1==c2 && length pvs==length pps &&
and [mightMatch v p|(v,p)<-zip pvs pps]
_ -> False
RecordValue rv ->
case p of
RecordPattern rp ->
and [maybe False (flip mightMatch p) (proj v l) | RecordRow l p<-rp]
_ -> False
_ -> True
patVars p =
case p of
PV x -> [x]
PAs x p -> x:patVars p
_ -> collectPattOp patVars p
convType = ppT
where
ppT t =
case t of
Table ti tv -> TableType (ppT ti) (ppT tv)
RecType rt -> RecordType (convFields rt)
-- App tf ta -> TAp (ppT tf) (ppT ta)
-- FV [] -> tcon0 (identS "({-empty variant-})")
Sort k -> convSort k
-- EInt n -> tcon0 (identS ("({-"++show n++"-})")) -- type level numeric literal
FV (t:ts) -> ppT t -- !!
QC (m,n) -> ParamType (ParamTypeId ((gQId m n)))
Q (m,n) -> ParamType (ParamTypeId ((gQId m n)))
_ -> error $ "Missing case in convType for: "++show t
convFields = map convField . filter (not.isLockLabel.fst)
convField (l,r) = RecordRow (lblId l) (ppT r)
convSort k = case showIdent k of
"Float" -> FloatType
"Int" -> IntType
"Str" -> StrType
_ -> error ("convSort "++show k)
toParamType t = case convType t of
ParamType pt -> pt
_ -> error ("toParamType "++show t)
toParamId t = case toParamType t of
ParamTypeId p -> p
paramType gr q@(_,n) =
case lookupOrigInfo gr q of
Ok (m,ResParam (Just (L _ ps)) _)
{- - | m/=cPredef && m/=moduleNameS "Prelude"-} ->
((S.singleton (m,n),argTypes ps),
[ParamDef name (map (param m) ps)]
)
where name = (gQId m n)
Ok (m,ResOper _ (Just (L _ t)))
| m==cPredef && n==cInts ->
((S.empty,S.empty),[]) {-
((S.singleton (m,n),S.empty),
[Type (ConAp ((gQId m n)) [identS "n"]) (TId (identS "Int"))])-}
| otherwise ->
((S.singleton (m,n),paramTypes gr t),
[ParamAliasDef ((gQId m n)) (convType t)])
_ -> ((S.empty,S.empty),[])
where
param m (n,ctx) = Param ((gQId m n)) [toParamId t|(_,_,t)<-ctx]
argTypes = S.unions . map argTypes1
argTypes1 (n,ctx) = S.unions [paramTypes gr t|(_,_,t)<-ctx]
lblId = LabelId . render -- hmm
modId (MN m) = ModId (showIdent m)
class FromIdent i where gId :: Ident -> i
instance FromIdent VarId where
gId i = if isWildIdent i then Anonymous else VarId (showIdent i)
instance FromIdent C.FunId where gId = C.FunId . showIdent
instance FromIdent CatId where gId = CatId . showIdent
instance FromIdent ParamId where gId = ParamId . unqual
instance FromIdent VarValueId where gId = VarValueId . unqual
class FromIdent i => QualIdent i where gQId :: ModuleName -> Ident -> i
instance QualIdent ParamId where gQId m n = ParamId (qual m n)
instance QualIdent VarValueId where gQId m n = VarValueId (qual m n)
qual m n = Qual (modId m) (showIdent n)
unqual n = Unqual (showIdent n)
convFlags gr mn =
Flags [(n,convLit v) |
(n,v)<-err (const []) (optionsPGF.mflags) (lookupModule gr mn)]
where
convLit l =
case l of
LStr s -> Str s
LInt i -> C.Int i
LFlt d -> Flt d

View File

@@ -1,4 +1,4 @@
{-# LANGUAGE BangPatterns, FlexibleContexts #-}
{-# LANGUAGE BangPatterns, FlexibleContexts, MagicHash #-}
module GF.Compile.GrammarToPGF (mkCanon2pgf) where
--import GF.Compile.Export
@@ -30,6 +30,10 @@ import qualified Data.Map as Map
import qualified Data.IntMap as IntMap
import Data.Array.IArray
import Data.Char
import GHC.Prim
import GHC.Base(getTag)
mkCanon2pgf :: Options -> SourceGrammar -> ModuleName -> IOE D.PGF
mkCanon2pgf opts gr am = do
(an,abs) <- mkAbstr am
@@ -59,7 +63,9 @@ mkCanon2pgf opts gr am = do
[(0,i2i f) | ((m,f),AbsFun (Just (L _ ty)) _ _ (Just True)) <- adefs, snd (GM.valCat ty) == cat]
mkConcr cm = do
let cflags = err (const noOptions) mflags (lookupModule gr cm)
let cflags = err (const noOptions) mflags (lookupModule gr cm)
ciCmp | flag optCaseSensitive cflags = compare
| otherwise = compareCaseInsensitve
(ex_seqs,cdefs) <- addMissingPMCFGs
Map.empty
@@ -68,15 +74,15 @@ mkCanon2pgf opts gr am = do
let flags = Map.fromList [(mkCId f,x) | (f,x) <- optionsPGF cflags]
seqs = (mkSetArray . Set.fromList . concat) $
seqs = (mkArray . sortNubBy ciCmp . concat) $
(Map.keys ex_seqs : [maybe [] elems (mseqs mi) | (m,mi) <- allExtends gr cm])
ex_seqs_arr = mkMapArray ex_seqs :: Array SeqId Sequence
!(!fid_cnt1,!cnccats) = genCncCats gr am cm cdefs
!(!fid_cnt2,!productions,!lindefs,!linrefs,!cncfuns)
= genCncFuns gr am cm ex_seqs_arr seqs cdefs fid_cnt1 cnccats
= genCncFuns gr am cm ex_seqs_arr ciCmp seqs cdefs fid_cnt1 cnccats
printnames = genPrintNames cdefs
return (mi2i cm, D.Concr flags
printnames
@@ -186,6 +192,7 @@ genCncFuns :: Grammar
-> ModuleName
-> ModuleName
-> Array SeqId Sequence
-> (Sequence -> Sequence -> Ordering)
-> Array SeqId Sequence
-> [(QIdent, Info)]
-> FId
@@ -195,7 +202,7 @@ genCncFuns :: Grammar
IntMap.IntMap [FunId],
IntMap.IntMap [FunId],
Array FunId D.CncFun)
genCncFuns gr am cm ex_seqs seqs cdefs fid_cnt cnccats =
genCncFuns gr am cm ex_seqs ciCmp seqs cdefs fid_cnt cnccats =
let (fid_cnt1,funs_cnt1,funs1,lindefs,linrefs) = mkCncCats cdefs fid_cnt 0 [] IntMap.empty IntMap.empty
(fid_cnt2,funs_cnt2,funs2,prods) = mkCncFuns cdefs fid_cnt1 funs_cnt1 funs1 lindefs Map.empty IntMap.empty
in (fid_cnt2,prods,lindefs,linrefs,array (0,funs_cnt2-1) funs2)
@@ -282,9 +289,9 @@ genCncFuns gr am cm ex_seqs seqs cdefs fid_cnt cnccats =
in (offs+funid0,C.CncFun (i2i id) (amap (newIndex mseqs) lins0)):funs
where
newIndex mseqs i = binSearch (mseqs ! i) seqs (bounds seqs)
binSearch v arr (i,j)
| i <= j = case compare v (arr ! k) of
| i <= j = case ciCmp v (arr ! k) of
LT -> binSearch v arr (i,k-1)
EQ -> k
GT -> binSearch v arr (k+1,j)
@@ -303,6 +310,121 @@ genPrintNames cdefs =
flatten (Alts x _) = flatten x
flatten (C x y) = flatten x +++ flatten y
--mkArray lst = listArray (0,length lst-1) lst
mkArray lst = listArray (0,length lst-1) lst
mkMapArray map = array (0,Map.size map-1) [(v,k) | (k,v) <- Map.toList map]
mkSetArray set = listArray (0,Set.size set-1) [v | v <- Set.toList set]
-- The following is a version of Data.List.sortBy which together
-- with the sorting also eliminates duplicate values
sortNubBy cmp = mergeAll . sequences
where
sequences (a:b:xs) =
case cmp a b of
GT -> descending b [a] xs
EQ -> sequences (b:xs)
LT -> ascending b (a:) xs
sequences xs = [xs]
descending a as [] = [a:as]
descending a as (b:bs) =
case cmp a b of
GT -> descending b (a:as) bs
EQ -> descending a as bs
LT -> (a:as) : sequences (b:bs)
ascending a as [] = let !x = as [a]
in [x]
ascending a as (b:bs) =
case cmp a b of
GT -> let !x = as [a]
in x : sequences (b:bs)
EQ -> ascending a as bs
LT -> ascending b (\ys -> as (a:ys)) bs
mergeAll [x] = x
mergeAll xs = mergeAll (mergePairs xs)
mergePairs (a:b:xs) = let !x = merge a b
in x : mergePairs xs
mergePairs xs = xs
merge as@(a:as') bs@(b:bs') =
case cmp a b of
GT -> b:merge as bs'
EQ -> a:merge as' bs'
LT -> a:merge as' bs
merge [] bs = bs
merge as [] = as
-- The following function does case-insensitive comparison of sequences.
-- This is used to allow case-insensitive parsing, while
-- the linearizer still has access to the original cases.
compareCaseInsensitve s1 s2 =
compareSeq (elems s1) (elems s2)
where
compareSeq [] [] = EQ
compareSeq [] _ = LT
compareSeq _ [] = GT
compareSeq (x:xs) (y:ys) =
case compareSym x y of
EQ -> compareSeq xs ys
x -> x
compareSym s1 s2 =
case s1 of
D.SymCat d1 r1
-> case s2 of
D.SymCat d2 r2
-> case compare d1 d2 of
EQ -> r1 `compare` r2
x -> x
_ -> LT
D.SymLit d1 r1
-> case s2 of
D.SymCat {} -> GT
D.SymLit d2 r2
-> case compare d1 d2 of
EQ -> r1 `compare` r2
x -> x
_ -> LT
D.SymVar d1 r1
-> if tagToEnum# (getTag s2 ># 2#)
then LT
else case s2 of
D.SymVar d2 r2
-> case compare d1 d2 of
EQ -> r1 `compare` r2
x -> x
_ -> GT
D.SymKS t1
-> if tagToEnum# (getTag s2 ># 3#)
then LT
else case s2 of
D.SymKS t2 -> t1 `compareToken` t2
_ -> GT
D.SymKP a1 b1
-> if tagToEnum# (getTag s2 ># 4#)
then LT
else case s2 of
D.SymKP a2 b2
-> case compare a1 a2 of
EQ -> b1 `compare` b2
x -> x
_ -> GT
_ -> let t1 = getTag s1
t2 = getTag s2
in if tagToEnum# (t1 <# t2)
then LT
else if tagToEnum# (t1 ==# t2)
then EQ
else GT
compareToken [] [] = EQ
compareToken [] _ = LT
compareToken _ [] = GT
compareToken (x:xs) (y:ys)
| x == y = compareToken xs ys
| otherwise = case compare (toLower x) (toLower y) of
EQ -> case compareToken xs ys of
EQ -> compare x y
x -> x
x -> x

View File

@@ -0,0 +1,156 @@
module GF.Compile.PGFtoJSON (pgf2json) where
import PGF (showCId)
import qualified PGF.Internal as M
import PGF.Internal (
Abstr,
CId,
CncCat(..),
CncFun(..),
Concr,
DotPos,
Equation(..),
Literal(..),
PArg(..),
PGF,
Production(..),
Symbol(..),
Type,
absname,
abstract,
cflags,
cnccats,
cncfuns,
concretes,
funs,
productions,
sequences,
totalCats
)
import qualified Text.JSON as JSON
import Text.JSON (JSValue(..))
import qualified Data.Array.IArray as Array
import Data.Map (Map)
import qualified Data.Set as Set
import qualified Data.Map as Map
import qualified Data.IntMap as IntMap
pgf2json :: PGF -> String
pgf2json pgf =
JSON.encode $ JSON.makeObj
[ ("abstract", json_abstract)
, ("concretes", json_concretes)
]
where
n = showCId $ absname pgf
as = abstract pgf
cs = Map.assocs (concretes pgf)
start = showCId $ M.lookStartCat pgf
json_abstract = abstract2json n start as
json_concretes = JSON.makeObj $ map concrete2json cs
abstract2json :: String -> String -> Abstr -> JSValue
abstract2json name start ds =
JSON.makeObj
[ ("name", mkJSStr name)
, ("startcat", mkJSStr start)
, ("funs", JSON.makeObj $ map absdef2json (Map.assocs (funs ds)))
]
absdef2json :: (CId,(Type,Int,Maybe ([Equation],[[M.Instr]]),Double)) -> (String,JSValue)
absdef2json (f,(typ,_,_,_)) = (showCId f,sig)
where
(args,cat) = M.catSkeleton typ
sig = JSON.makeObj
[ ("args", JSArray $ map (mkJSStr.showCId) args)
, ("cat", mkJSStr $ showCId cat)
]
lit2json :: Literal -> JSValue
lit2json (LStr s) = mkJSStr s
lit2json (LInt n) = mkJSInt n
lit2json (LFlt d) = JSRational True (toRational d)
concrete2json :: (CId,Concr) -> (String,JSValue)
concrete2json (c,cnc) = (showCId c,obj)
where
obj = JSON.makeObj
[ ("flags", JSON.makeObj [ (showCId k, lit2json v) | (k,v) <- Map.toList (cflags cnc) ])
, ("productions", JSON.makeObj [ (show cat, JSArray (map frule2json (Set.toList set))) | (cat,set) <- IntMap.toList (productions cnc)])
, ("functions", JSArray (map ffun2json (Array.elems (cncfuns cnc))))
, ("sequences", JSArray (map seq2json (Array.elems (sequences cnc))))
, ("categories", JSON.makeObj $ map cats2json (Map.assocs (cnccats cnc)))
, ("totalfids", mkJSInt (totalCats cnc))
]
cats2json :: (CId, CncCat) -> (String,JSValue)
cats2json (c,CncCat start end _) = (showCId c, ixs)
where
ixs = JSON.makeObj
[ ("start", mkJSInt start)
, ("end", mkJSInt end)
]
frule2json :: Production -> JSValue
frule2json (PApply fid args) =
JSON.makeObj
[ ("type", mkJSStr "Apply")
, ("fid", mkJSInt fid)
, ("args", JSArray (map farg2json args))
]
frule2json (PCoerce arg) =
JSON.makeObj
[ ("type", mkJSStr "Coerce")
, ("arg", mkJSInt arg)
]
farg2json :: PArg -> JSValue
farg2json (PArg hypos fid) =
JSON.makeObj
[ ("type", mkJSStr "PArg")
, ("hypos", JSArray $ map (mkJSInt . snd) hypos)
, ("fid", mkJSInt fid)
]
ffun2json :: CncFun -> JSValue
ffun2json (CncFun f lins) =
JSON.makeObj
[ ("name", mkJSStr $ showCId f)
, ("lins", JSArray (map mkJSInt (Array.elems lins)))
]
seq2json :: Array.Array DotPos Symbol -> JSValue
seq2json seq = JSArray [sym2json s | s <- Array.elems seq]
sym2json :: Symbol -> JSValue
sym2json (SymCat n l) = new "SymCat" [mkJSInt n, mkJSInt l]
sym2json (SymLit n l) = new "SymLit" [mkJSInt n, mkJSInt l]
sym2json (SymVar n l) = new "SymVar" [mkJSInt n, mkJSInt l]
sym2json (SymKS t) = new "SymKS" [mkJSStr t]
sym2json (SymKP ts alts) = new "SymKP" [JSArray (map sym2json ts), JSArray (map alt2json alts)]
sym2json SymBIND = new "SymKS" [mkJSStr "&+"]
sym2json SymSOFT_BIND = new "SymKS" [mkJSStr "&+"]
sym2json SymSOFT_SPACE = new "SymKS" [mkJSStr "&+"]
sym2json SymCAPIT = new "SymKS" [mkJSStr "&|"]
sym2json SymALL_CAPIT = new "SymKS" [mkJSStr "&|"]
sym2json SymNE = new "SymNE" []
alt2json :: ([Symbol],[String]) -> JSValue
alt2json (ps,ts) = new "Alt" [JSArray (map sym2json ps), JSArray (map mkJSStr ts)]
new :: String -> [JSValue] -> JSValue
new f xs =
JSON.makeObj
[ ("type", mkJSStr f)
, ("args", JSArray xs)
]
-- | Make JSON value from string
mkJSStr :: String -> JSValue
mkJSStr = JSString . JSON.toJSString
-- | Make JSON value from integer
mkJSInt :: Integral a => a -> JSValue
mkJSInt = JSRational False . toRational

View File

@@ -360,12 +360,13 @@ getOverload gr g mt ot = case appForm ot of
nest 2 (showTypes pre)
return (mkApp fun tts, val)
([],[]) -> do
checkError $ "no overload instance of" <+> ppTerm Unqualified 0 f $$
"for" $$
checkError $ "no overload instance of" <+> ppTerm Qualified 0 f $$
maybe empty (\x -> "with value type" <+> ppType x) mt $$
"for argument list" $$
nest 2 stysError $$
"among" $$
nest 2 (vcat stypsError) $$
maybe empty (\x -> "with value type" <+> ppType x) mt
"among alternatives" $$
nest 2 (vcat stypsError)
(vfs1,vfs2) -> case (noProds vfs1,noProds vfs2) of
([(val,fun)],_) -> do

View File

@@ -0,0 +1,232 @@
{
"$schema": "http://json-schema.org/draft-07/schema#",
"$id": "http://grammaticalframework.org/pgf.schema.json",
"type": "object",
"title": "PGF JSON Schema",
"required": [
"abstract",
"concretes"
],
"properties": {
"abstract": {
"type": "object",
"required": [
"name",
"startcat",
"funs"
],
"properties": {
"name": {
"type": "string"
},
"startcat": {
"type": "string"
},
"funs": {
"type": "object",
"additionalProperties": {
"type": "object",
"required": [
"args",
"cat"
],
"properties": {
"args": {
"type": "array",
"items": {
"type": "string"
}
},
"cat": {
"type": "string"
}
}
}
}
}
},
"concretes": {
"type": "object",
"additionalProperties": {
"required": [
"flags",
"productions",
"functions",
"sequences",
"categories",
"totalfids"
],
"properties": {
"flags": {
"type": "object",
"additionalProperties": {
"type": ["string", "number"]
}
},
"productions": {
"type": "object",
"additionalProperties": {
"type": "array",
"items": {
"oneOf": [
{
"$ref": "#/definitions/apply"
},
{
"$ref": "#/definitions/coerce"
}
]
}
}
},
"functions": {
"type": "array",
"items": {
"title": "CncFun",
"type": "object",
"properties": {
"name": {
"type": "string"
},
"lins": {
"type": "array",
"items": {
"type": "integer"
}
}
}
}
},
"sequences": {
"type": "array",
"items": {
"type": "array",
"items": {
"$ref": "#/definitions/sym"
}
}
},
"categories": {
"type": "object",
"additionalProperties": {
"title": "CncCat",
"type": "object",
"required": [
"start",
"end"
],
"properties": {
"start": {
"type": "integer"
},
"end": {
"type": "integer"
}
}
}
},
"totalfids": {
"type": "integer"
}
}
}
}
},
"definitions": {
"apply": {
"required": [
"type",
"fid",
"args"
],
"properties": {
"type": {
"type": "string",
"enum": ["Apply"]
},
"fid": {
"type": "integer"
},
"args": {
"type": "array",
"items": {
"$ref": "#/definitions/parg"
}
}
}
},
"coerce": {
"required": [
"type",
"arg"
],
"properties": {
"type": {
"type": "string",
"enum": ["Coerce"]
},
"arg": {
"type": "integer"
}
}
},
"parg": {
"required": [
"type",
"hypos",
"fid"
],
"properties": {
"type": {
"type": "string",
"enum": ["PArg"]
},
"hypos": {
"type": "array",
"items": {
"type": "integer"
}
},
"fid": {
"type": "integer"
}
}
},
"sym": {
"title": "Sym",
"required": [
"type",
"args"
],
"properties": {
"type": {
"type": "string",
"enum": [
"SymCat",
"SymLit",
"SymVar",
"SymKS",
"SymKP",
"SymNE"
]
},
"args": {
"type": "array",
"items": {
"anyOf": [
{
"type": "string"
},
{
"type": "integer"
},
{
"$ref": "#/definitions/sym"
}
]
}
}
}
}
}
}

View File

@@ -7,6 +7,7 @@ import GF.Compile as S(batchCompile,link,srcAbsName)
import GF.CompileInParallel as P(parallelBatchCompile)
import GF.Compile.Export
import GF.Compile.ConcreteToHaskell(concretes2haskell)
import GF.Compile.GrammarToCanonical--(concretes2canonical)
import GF.Compile.CFGtoPGF
import GF.Compile.GetGrammar
import GF.Grammar.BNFC
@@ -17,12 +18,13 @@ import GF.Infra.UseIO
import GF.Infra.Option
import GF.Data.ErrM
import GF.System.Directory
import GF.Text.Pretty(render)
import GF.Text.Pretty(render,render80)
import Data.Maybe
import qualified Data.Map as Map
import qualified Data.Set as Set
import qualified Data.ByteString.Lazy as BSL
import GF.Grammar.CanonicalJSON (encodeJSON)
import System.FilePath
import Control.Monad(when,unless,forM_)
@@ -47,7 +49,7 @@ mainGFC opts fs = do
compileSourceFiles :: Options -> [FilePath] -> IOE ()
compileSourceFiles opts fs =
do output <- batchCompile opts fs
cncs2haskell output
exportCanonical output
unless (flag optStopAfterPhase opts == Compile) $
linkGrammars opts output
where
@@ -55,15 +57,35 @@ compileSourceFiles opts fs =
batchCompile' opts fs = do (t,cnc_gr) <- S.batchCompile opts fs
return (t,[cnc_gr])
cncs2haskell output =
when (FmtHaskell `elem` flag optOutputFormats opts &&
haskellOption opts HaskellConcrete) $
mapM_ cnc2haskell (snd output)
exportCanonical (_time, canonical) =
do when (FmtHaskell `elem` ofmts && haskellOption opts HaskellConcrete) $
mapM_ cnc2haskell canonical
when (FmtCanonicalGF `elem` ofmts) $
do createDirectoryIfMissing False "canonical"
mapM_ abs2canonical canonical
mapM_ cnc2canonical canonical
when (FmtCanonicalJson `elem` ofmts) $ mapM_ grammar2json canonical
where
ofmts = flag optOutputFormats opts
cnc2haskell (cnc,gr) =
mapM_ writeHs $ concretes2haskell opts (srcAbsName gr cnc) gr
do mapM_ writeExport $ concretes2haskell opts (srcAbsName gr cnc) gr
writeHs (path,s) = writing opts path $ writeUTF8File path s
abs2canonical (cnc,gr) =
writeExport ("canonical/"++render absname++".gf",render80 canAbs)
where
absname = srcAbsName gr cnc
canAbs = abstract2canonical absname gr
cnc2canonical (cnc,gr) =
mapM_ (writeExport.fmap render80) $
concretes2canonical opts (srcAbsName gr cnc) gr
grammar2json (cnc,gr) = encodeJSON (render absname ++ ".json") gr_canon
where absname = srcAbsName gr cnc
gr_canon = grammar2canonical opts absname gr
writeExport (path,s) = writing opts path $ writeUTF8File path s
-- | Create a @.pgf@ file (and possibly files in other formats, if specified
@@ -80,7 +102,9 @@ linkGrammars opts (t_src,~cnc_grs@(~(cnc,gr):_)) =
if t_pgf >= Just t_src
then putIfVerb opts $ pgfFile ++ " is up-to-date."
else do pgfs <- mapM (link opts) cnc_grs
let pgf = foldl1 unionPGF pgfs
let pgf0 = foldl1 unionPGF pgfs
probs <- maybe (return . defaultProbabilities) readProbabilitiesFromFile (flag optProbsFile opts) pgf0
let pgf = setProbabilities probs pgf0
writePGF opts pgf
writeOutputs opts pgf
@@ -115,7 +139,9 @@ unionPGFFiles opts fs =
doIt =
do pgfs <- mapM readPGFVerbose fs
let pgf0 = foldl1 unionPGF pgfs
pgf = if flag optOptimizePGF opts then optimizePGF pgf0 else pgf0
pgf1 = if flag optOptimizePGF opts then optimizePGF pgf0 else pgf0
probs <- liftIO (maybe (return . defaultProbabilities) readProbabilitiesFromFile (flag optProbsFile opts) pgf1)
let pgf = setProbabilities probs pgf1
pgfFile = outputPath opts (grammarName opts pgf <.> "pgf")
if pgfFile `elem` fs
then putStrLnE $ "Refusing to overwrite " ++ pgfFile

View File

@@ -0,0 +1,313 @@
-- |
-- Module : GF.Grammar.Canonical
-- Stability : provisional
--
-- Abstract syntax for canonical GF grammars, i.e. what's left after
-- high-level constructions such as functors and opers have been eliminated
-- by partial evaluation. This is intended as a common intermediate
-- representation to simplify export to other formats.
{-# LANGUAGE DeriveTraversable #-}
module GF.Grammar.Canonical where
import Prelude hiding ((<>))
import GF.Text.Pretty
-- | A Complete grammar
data Grammar = Grammar Abstract [Concrete] deriving Show
--------------------------------------------------------------------------------
-- ** Abstract Syntax
-- | Abstract Syntax
data Abstract = Abstract ModId Flags [CatDef] [FunDef] deriving Show
abstrName (Abstract mn _ _ _) = mn
data CatDef = CatDef CatId [CatId] deriving Show
data FunDef = FunDef FunId Type deriving Show
data Type = Type [TypeBinding] TypeApp deriving Show
data TypeApp = TypeApp CatId [Type] deriving Show
data TypeBinding = TypeBinding VarId Type deriving Show
--------------------------------------------------------------------------------
-- ** Concreate syntax
-- | Concrete Syntax
data Concrete = Concrete ModId ModId Flags [ParamDef] [LincatDef] [LinDef]
deriving Show
concName (Concrete cnc _ _ _ _ _) = cnc
data ParamDef = ParamDef ParamId [ParamValueDef]
| ParamAliasDef ParamId LinType
deriving Show
data LincatDef = LincatDef CatId LinType deriving Show
data LinDef = LinDef FunId [VarId] LinValue deriving Show
-- | Linearization type, RHS of @lincat@
data LinType = FloatType
| IntType
| ParamType ParamType
| RecordType [RecordRowType]
| StrType
| TableType LinType LinType
| TupleType [LinType]
deriving (Eq,Ord,Show)
newtype ParamType = ParamTypeId ParamId deriving (Eq,Ord,Show)
-- | Linearization value, RHS of @lin@
data LinValue = ConcatValue LinValue LinValue
| LiteralValue LinLiteral
| ErrorValue String
| ParamConstant ParamValue
| PredefValue PredefId
| RecordValue [RecordRowValue]
| TableValue LinType [TableRowValue]
--- | VTableValue LinType [LinValue]
| TupleValue [LinValue]
| VariantValue [LinValue]
| VarValue VarValueId
| PreValue [([String], LinValue)] LinValue
| Projection LinValue LabelId
| Selection LinValue LinValue
| CommentedValue String LinValue
deriving (Eq,Ord,Show)
data LinLiteral = FloatConstant Float
| IntConstant Int
| StrConstant String
deriving (Eq,Ord,Show)
data LinPattern = ParamPattern ParamPattern
| RecordPattern [RecordRow LinPattern]
| TuplePattern [LinPattern]
| WildPattern
deriving (Eq,Ord,Show)
type ParamValue = Param LinValue
type ParamPattern = Param LinPattern
type ParamValueDef = Param ParamId
data Param arg = Param ParamId [arg]
deriving (Eq,Ord,Show,Functor,Foldable,Traversable)
type RecordRowType = RecordRow LinType
type RecordRowValue = RecordRow LinValue
type TableRowValue = TableRow LinValue
data RecordRow rhs = RecordRow LabelId rhs
deriving (Eq,Ord,Show,Functor,Foldable,Traversable)
data TableRow rhs = TableRow LinPattern rhs
deriving (Eq,Ord,Show,Functor,Foldable,Traversable)
-- *** Identifiers in Concrete Syntax
newtype PredefId = PredefId Id deriving (Eq,Ord,Show)
newtype LabelId = LabelId Id deriving (Eq,Ord,Show)
data VarValueId = VarValueId QualId deriving (Eq,Ord,Show)
-- | Name of param type or param value
newtype ParamId = ParamId QualId deriving (Eq,Ord,Show)
--------------------------------------------------------------------------------
-- ** Used in both Abstract and Concrete Syntax
newtype ModId = ModId Id deriving (Eq,Ord,Show)
newtype CatId = CatId Id deriving (Eq,Ord,Show)
newtype FunId = FunId Id deriving (Eq,Show)
data VarId = Anonymous | VarId Id deriving Show
newtype Flags = Flags [(FlagName,FlagValue)] deriving Show
type FlagName = Id
data FlagValue = Str String | Int Int | Flt Double deriving Show
-- *** Identifiers
type Id = String
data QualId = Qual ModId Id | Unqual Id deriving (Eq,Ord,Show)
--------------------------------------------------------------------------------
-- ** Pretty printing
instance Pretty Grammar where
pp (Grammar abs cncs) = abs $+$ vcat cncs
instance Pretty Abstract where
pp (Abstract m flags cats funs) =
"abstract" <+> m <+> "=" <+> "{" $$
flags $$
"cat" <+> fsep cats $$
"fun" <+> vcat funs $$
"}"
instance Pretty CatDef where
pp (CatDef c cs) = hsep (c:cs)<>";"
instance Pretty FunDef where
pp (FunDef f ty) = f <+> ":" <+> ty <>";"
instance Pretty Type where
pp (Type bs ty) = sep (punctuate " ->" (map pp bs ++ [pp ty]))
instance PPA Type where
ppA (Type [] (TypeApp c [])) = pp c
ppA t = parens t
instance Pretty TypeBinding where
pp (TypeBinding Anonymous (Type [] tapp)) = pp tapp
pp (TypeBinding Anonymous ty) = parens ty
pp (TypeBinding (VarId x) ty) = parens (x<+>":"<+>ty)
instance Pretty TypeApp where
pp (TypeApp c targs) = c<+>hsep (map ppA targs)
instance Pretty VarId where
pp Anonymous = pp "_"
pp (VarId x) = pp x
--------------------------------------------------------------------------------
instance Pretty Concrete where
pp (Concrete cncid absid flags params lincats lins) =
"concrete" <+> cncid <+> "of" <+> absid <+> "=" <+> "{" $$
vcat params $$
section "lincat" lincats $$
section "lin" lins $$
"}"
where
section name [] = empty
section name ds = name <+> vcat (map (<> ";") ds)
instance Pretty ParamDef where
pp (ParamDef p pvs) = hang ("param"<+> p <+> "=") 4 (punctuate " |" pvs)<>";"
pp (ParamAliasDef p t) = hang ("oper"<+> p <+> "=") 4 t<>";"
instance PPA arg => Pretty (Param arg) where
pp (Param p ps) = pp p<+>sep (map ppA ps)
instance PPA arg => PPA (Param arg) where
ppA (Param p []) = pp p
ppA pv = parens pv
instance Pretty LincatDef where
pp (LincatDef c lt) = hang (c <+> "=") 4 lt
instance Pretty LinType where
pp lt = case lt of
FloatType -> pp "Float"
IntType -> pp "Int"
ParamType pt -> pp pt
RecordType rs -> block rs
StrType -> pp "Str"
TableType pt lt -> sep [pt <+> "=>",pp lt]
TupleType lts -> "<"<>punctuate "," lts<>">"
instance RhsSeparator LinType where rhsSep _ = pp ":"
instance Pretty ParamType where
pp (ParamTypeId p) = pp p
instance Pretty LinDef where
pp (LinDef f xs lv) = hang (f<+>hsep xs<+>"=") 4 lv
instance Pretty LinValue where
pp lv = case lv of
ConcatValue v1 v2 -> sep [v1 <+> "++",pp v2]
ErrorValue s -> "Predef.error"<+>doubleQuotes s
ParamConstant pv -> pp pv
Projection lv l -> ppA lv<>"."<>l
Selection tv pv -> ppA tv<>"!"<>ppA pv
VariantValue vs -> "variants"<+>block vs
CommentedValue s v -> "{-" <+> s <+> "-}" $$ v
_ -> ppA lv
instance PPA LinValue where
ppA lv = case lv of
LiteralValue l -> ppA l
ParamConstant pv -> ppA pv
PredefValue p -> ppA p
RecordValue [] -> pp "<>"
RecordValue rvs -> block rvs
PreValue alts def ->
"pre"<+>block (map alt alts++["_"<+>"=>"<+>def])
where
alt (ss,lv) = hang (hcat (punctuate "|" (map doubleQuotes ss)))
2 ("=>"<+>lv)
TableValue _ tvs -> "table"<+>block tvs
-- VTableValue t ts -> "table"<+>t<+>brackets (semiSep ts)
TupleValue lvs -> "<"<>punctuate "," lvs<>">"
VarValue v -> pp v
_ -> parens lv
instance Pretty LinLiteral where pp = ppA
instance PPA LinLiteral where
ppA l = case l of
FloatConstant f -> pp f
IntConstant n -> pp n
StrConstant s -> doubleQuotes s -- hmm
instance RhsSeparator LinValue where rhsSep _ = pp "="
instance Pretty LinPattern where
pp p =
case p of
ParamPattern pv -> pp pv
_ -> ppA p
instance PPA LinPattern where
ppA p =
case p of
ParamPattern pv -> ppA pv
RecordPattern r -> block r
TuplePattern ps -> "<"<>punctuate "," ps<>">"
WildPattern -> pp "_"
_ -> parens p
instance RhsSeparator LinPattern where rhsSep _ = pp "="
instance RhsSeparator rhs => Pretty (RecordRow rhs) where
pp (RecordRow l v) = hang (l<+>rhsSep v) 2 v
instance Pretty rhs => Pretty (TableRow rhs) where
pp (TableRow l v) = hang (l<+>"=>") 2 v
--------------------------------------------------------------------------------
instance Pretty ModId where pp (ModId s) = pp s
instance Pretty CatId where pp (CatId s) = pp s
instance Pretty FunId where pp (FunId s) = pp s
instance Pretty LabelId where pp (LabelId s) = pp s
instance Pretty PredefId where pp = ppA
instance PPA PredefId where ppA (PredefId s) = "Predef."<>s
instance Pretty ParamId where pp = ppA
instance PPA ParamId where ppA (ParamId s) = pp s
instance Pretty VarValueId where pp (VarValueId s) = pp s
instance Pretty QualId where pp = ppA
instance PPA QualId where
ppA (Qual m n) = m<>"_"<>n -- hmm
ppA (Unqual n) = pp n
instance Pretty Flags where
pp (Flags []) = empty
pp (Flags flags) = "flags" <+> vcat (map ppFlag flags)
where
ppFlag (name,value) = name <+> "=" <+> value <>";"
instance Pretty FlagValue where
pp (Str s) = pp s
pp (Int i) = pp i
pp (Flt d) = pp d
--------------------------------------------------------------------------------
-- | Pretty print atomically (i.e. wrap it in parentheses if necessary)
class Pretty a => PPA a where ppA :: a -> Doc
class Pretty rhs => RhsSeparator rhs where rhsSep :: rhs -> Doc
semiSep xs = punctuate ";" xs
block xs = braces (semiSep xs)

View File

@@ -0,0 +1,289 @@
module GF.Grammar.CanonicalJSON (
encodeJSON
) where
import Text.JSON
import Control.Applicative ((<|>))
import Data.Ratio (denominator, numerator)
import GF.Grammar.Canonical
encodeJSON :: FilePath -> Grammar -> IO ()
encodeJSON fpath g = writeFile fpath (encode g)
-- in general we encode grammars using JSON objects/records,
-- except for newtypes/coercions/direct values
-- the top-level definitions use normal record labels,
-- but recursive types/values/ids use labels staring with a "."
instance JSON Grammar where
showJSON (Grammar abs cncs) = makeObj [("abstract", showJSON abs), ("concretes", showJSON cncs)]
readJSON o = Grammar <$> o!"abstract" <*> o!"concretes"
--------------------------------------------------------------------------------
-- ** Abstract Syntax
instance JSON Abstract where
showJSON (Abstract absid flags cats funs)
= makeObj [("abs", showJSON absid),
("flags", showJSON flags),
("cats", showJSON cats),
("funs", showJSON funs)]
readJSON o = Abstract
<$> o!"abs"
<*>(o!"flags" <|> return (Flags []))
<*> o!"cats"
<*> o!"funs"
instance JSON CatDef where
-- non-dependent categories are encoded as simple strings:
showJSON (CatDef c []) = showJSON c
showJSON (CatDef c cs) = makeObj [("cat", showJSON c), ("args", showJSON cs)]
readJSON o = CatDef <$> readJSON o <*> return []
<|> CatDef <$> o!"cat" <*> o!"args"
instance JSON FunDef where
showJSON (FunDef f ty) = makeObj [("fun", showJSON f), ("type", showJSON ty)]
readJSON o = FunDef <$> o!"fun" <*> o!"type"
instance JSON Type where
showJSON (Type bs ty) = makeObj [(".args", showJSON bs), (".result", showJSON ty)]
readJSON o = Type <$> o!".args" <*> o!".result"
instance JSON TypeApp where
-- non-dependent categories are encoded as simple strings:
showJSON (TypeApp c []) = showJSON c
showJSON (TypeApp c args) = makeObj [(".cat", showJSON c), (".args", showJSON args)]
readJSON o = TypeApp <$> readJSON o <*> return []
<|> TypeApp <$> o!".cat" <*> o!".args"
instance JSON TypeBinding where
-- non-dependent categories are encoded as simple strings:
showJSON (TypeBinding Anonymous (Type [] (TypeApp c []))) = showJSON c
showJSON (TypeBinding x ty) = makeObj [(".var", showJSON x), (".type", showJSON ty)]
readJSON o = do c <- readJSON o
return (TypeBinding Anonymous (Type [] (TypeApp c [])))
<|> TypeBinding <$> o!".var" <*> o!".type"
--------------------------------------------------------------------------------
-- ** Concrete syntax
instance JSON Concrete where
showJSON (Concrete cncid absid flags params lincats lins)
= makeObj [("cnc", showJSON cncid),
("abs", showJSON absid),
("flags", showJSON flags),
("params", showJSON params),
("lincats", showJSON lincats),
("lins", showJSON lins)]
readJSON o = Concrete
<$> o!"cnc"
<*> o!"abs"
<*>(o!"flags" <|> return (Flags []))
<*> o!"params"
<*> o!"lincats"
<*> o!"lins"
instance JSON ParamDef where
showJSON (ParamDef p pvs) = makeObj [("param", showJSON p), ("values", showJSON pvs)]
showJSON (ParamAliasDef p t) = makeObj [("param", showJSON p), ("alias", showJSON t)]
readJSON o = ParamDef <$> o!"param" <*> o!"values"
<|> ParamAliasDef <$> o!"param" <*> o!"alias"
instance JSON LincatDef where
showJSON (LincatDef c lt) = makeObj [("cat", showJSON c), ("lintype", showJSON lt)]
readJSON o = LincatDef <$> o!"cat" <*> o!"lintype"
instance JSON LinDef where
showJSON (LinDef f xs lv) = makeObj [("fun", showJSON f), ("args", showJSON xs), ("lin", showJSON lv)]
readJSON o = LinDef <$> o!"fun" <*> o!"args" <*> o!"lin"
instance JSON LinType where
-- the basic types (Str, Float, Int) are encoded as strings:
showJSON (StrType) = showJSON "Str"
showJSON (FloatType) = showJSON "Float"
showJSON (IntType) = showJSON "Int"
-- parameters are also encoded as strings:
showJSON (ParamType pt) = showJSON pt
-- tables/tuples are encoded as JSON objects:
showJSON (TableType pt lt) = makeObj [(".tblarg", showJSON pt), (".tblval", showJSON lt)]
showJSON (TupleType lts) = makeObj [(".tuple", showJSON lts)]
-- records are encoded as records:
showJSON (RecordType rows) = showJSON rows
readJSON o = do "Str" <- readJSON o; return StrType
<|> do "Float" <- readJSON o; return FloatType
<|> do "Int" <- readJSON o; return IntType
<|> do ptype <- readJSON o; return (ParamType ptype)
<|> TableType <$> o!".tblarg" <*> o!".tblval"
<|> TupleType <$> o!".tuple"
<|> RecordType <$> readJSON o
instance JSON LinValue where
showJSON (LiteralValue l ) = showJSON l
-- most values are encoded as JSON objects:
showJSON (ParamConstant pv) = makeObj [(".param", showJSON pv)]
showJSON (PredefValue p ) = makeObj [(".predef", showJSON p)]
showJSON (TableValue t tvs) = makeObj [(".tblarg", showJSON t), (".tblrows", showJSON tvs)]
showJSON (TupleValue lvs) = makeObj [(".tuple", showJSON lvs)]
showJSON (VarValue v ) = makeObj [(".var", showJSON v)]
showJSON (ErrorValue s ) = makeObj [(".error", showJSON s)]
showJSON (Projection lv l ) = makeObj [(".project", showJSON lv), (".label", showJSON l)]
showJSON (Selection tv pv) = makeObj [(".select", showJSON tv), (".key", showJSON pv)]
showJSON (VariantValue vs) = makeObj [(".variants", showJSON vs)]
showJSON (PreValue pre def) = makeObj [(".pre", showJSON pre),(".default", showJSON def)]
-- records are encoded directly as JSON records:
showJSON (RecordValue rows) = showJSON rows
-- concatenation is encoded as a JSON array:
showJSON v@(ConcatValue _ _) = showJSON (flatten v [])
where flatten (ConcatValue v v') = flatten v . flatten v'
flatten v = (v :)
readJSON o = LiteralValue <$> readJSON o
<|> ParamConstant <$> o!".param"
<|> PredefValue <$> o!".predef"
<|> TableValue <$> o!".tblarg" <*> o!".tblrows"
<|> TupleValue <$> o!".tuple"
<|> VarValue <$> o!".var"
<|> ErrorValue <$> o!".error"
<|> Projection <$> o!".project" <*> o!".label"
<|> Selection <$> o!".select" <*> o!".key"
<|> VariantValue <$> o!".variants"
<|> PreValue <$> o!".pre" <*> o!".default"
<|> RecordValue <$> readJSON o
<|> do vs <- readJSON o :: Result [LinValue]
return (foldr1 ConcatValue vs)
instance JSON LinLiteral where
-- basic values (Str, Float, Int) are encoded as JSON strings/numbers:
showJSON (StrConstant s) = showJSON s
showJSON (FloatConstant f) = showJSON f
showJSON (IntConstant n) = showJSON n
readJSON = readBasicJSON StrConstant IntConstant FloatConstant
instance JSON LinPattern where
-- wildcards and patterns without arguments are encoded as strings:
showJSON (WildPattern) = showJSON "_"
showJSON (ParamPattern (Param p [])) = showJSON p
-- complex patterns are encoded as JSON objects:
showJSON (ParamPattern pv) = showJSON pv
-- and records as records:
showJSON (RecordPattern r) = showJSON r
readJSON o = do "_" <- readJSON o; return WildPattern
<|> do p <- readJSON o; return (ParamPattern (Param p []))
<|> ParamPattern <$> readJSON o
<|> RecordPattern <$> readJSON o
instance JSON arg => JSON (Param arg) where
-- parameters without arguments are encoded as strings:
showJSON (Param p []) = showJSON p
showJSON (Param p args) = makeObj [(".paramid", showJSON p), (".args", showJSON args)]
readJSON o = Param <$> readJSON o <*> return []
<|> Param <$> o!".paramid" <*> o!".args"
instance JSON a => JSON (RecordRow a) where
-- record rows and lists of record rows are both encoded as JSON records (i.e., objects)
showJSON row = showJSONs [row]
showJSONs rows = makeObj (map toRow rows)
where toRow (RecordRow (LabelId lbl) val) = (lbl, showJSON val)
readJSON obj = head <$> readJSONs obj
readJSONs obj = mapM fromRow (assocsJSObject obj)
where fromRow (lbl, jsvalue) = do value <- readJSON jsvalue
return (RecordRow (LabelId lbl) value)
instance JSON rhs => JSON (TableRow rhs) where
showJSON (TableRow l v) = makeObj [(".pattern", showJSON l), (".value", showJSON v)]
readJSON o = TableRow <$> o!".pattern" <*> o!".value"
-- *** Identifiers in Concrete Syntax
instance JSON PredefId where showJSON (PredefId s) = showJSON s ; readJSON = fmap PredefId . readJSON
instance JSON LabelId where showJSON (LabelId s) = showJSON s ; readJSON = fmap LabelId . readJSON
instance JSON VarValueId where showJSON (VarValueId s) = showJSON s ; readJSON = fmap VarValueId . readJSON
instance JSON ParamId where showJSON (ParamId s) = showJSON s ; readJSON = fmap ParamId . readJSON
instance JSON ParamType where showJSON (ParamTypeId s) = showJSON s ; readJSON = fmap ParamTypeId . readJSON
--------------------------------------------------------------------------------
-- ** Used in both Abstract and Concrete Syntax
instance JSON ModId where showJSON (ModId s) = showJSON s ; readJSON = fmap ModId . readJSON
instance JSON CatId where showJSON (CatId s) = showJSON s ; readJSON = fmap CatId . readJSON
instance JSON FunId where showJSON (FunId s) = showJSON s ; readJSON = fmap FunId . readJSON
instance JSON VarId where
-- the anonymous variable is the underscore:
showJSON Anonymous = showJSON "_"
showJSON (VarId x) = showJSON x
readJSON o = do "_" <- readJSON o; return Anonymous
<|> VarId <$> readJSON o
instance JSON QualId where
showJSON (Qual (ModId m) n) = showJSON (m++"."++n)
showJSON (Unqual n) = showJSON n
readJSON o = do qualid <- readJSON o
let (mod, id) = span (/= '.') qualid
return $ if null mod then Unqual id else Qual (ModId mod) id
instance JSON Flags where
-- flags are encoded directly as JSON records (i.e., objects):
showJSON (Flags fs) = makeObj [(f, showJSON v) | (f, v) <- fs]
readJSON obj = Flags <$> mapM fromRow (assocsJSObject obj)
where fromRow (lbl, jsvalue) = do value <- readJSON jsvalue
return (lbl, value)
instance JSON FlagValue where
-- flag values are encoded as basic JSON types:
showJSON (Str s) = showJSON s
showJSON (Int i) = showJSON i
showJSON (Flt f) = showJSON f
readJSON = readBasicJSON Str Int Flt
--------------------------------------------------------------------------------
-- ** Convenience functions
(!) :: JSON a => JSValue -> String -> Result a
obj ! key = maybe (fail $ "CanonicalJSON.(!): Could not find key: " ++ show key)
readJSON
(lookup key (assocsJSObject obj))
assocsJSObject :: JSValue -> [(String, JSValue)]
assocsJSObject (JSObject o) = fromJSObject o
assocsJSObject (JSArray _) = fail $ "CanonicalJSON.assocsJSObject: Expected a JSON object, found an Array"
assocsJSObject jsvalue = fail $ "CanonicalJSON.assocsJSObject: Expected a JSON object, found " ++ show jsvalue
readBasicJSON :: (JSON int, Integral int, JSON flt, RealFloat flt) =>
(String -> v) -> (int -> v) -> (flt -> v) -> JSValue -> Result v
readBasicJSON str int flt o
= str <$> readJSON o
<|> int_or_flt <$> readJSON o
where int_or_flt f | f == fromIntegral n = int n
| otherwise = flt f
where n = round f

View File

@@ -209,7 +209,7 @@ ppTerm q d (S x y) = case x of
ppTerm q d (ExtR x y) = prec d 3 (ppTerm q 3 x <+> "**" <+> ppTerm q 4 y)
ppTerm q d (App x y) = prec d 4 (ppTerm q 4 x <+> ppTerm q 5 y)
ppTerm q d (V e es) = hang "table" 2 (sep [ppTerm q 6 e,brackets (fsep (punctuate ';' (map (ppTerm q 0) es)))])
ppTerm q d (FV es) = "variants" <+> braces (fsep (punctuate ';' (map (ppTerm q 0) es)))
ppTerm q d (FV es) = prec d 4 ("variants" <+> braces (fsep (punctuate ';' (map (ppTerm q 0) es))))
ppTerm q d (AdHocOverload es) = "overload" <+> braces (fsep (punctuate ';' (map (ppTerm q 0) es)))
ppTerm q d (Alts e xs) = prec d 4 ("pre" <+> braces (ppTerm q 0 e <> ';' <+> fsep (punctuate ';' (map (ppAltern q) xs))))
ppTerm q d (Strs es) = "strs" <+> braces (fsep (punctuate ';' (map (ppTerm q 0) es)))

View File

@@ -40,6 +40,9 @@ tvar = TId
tcon0 = TId
tcon c = foldl TAp (TId c)
lets [] e = e
lets ds e = Lets ds e
let1 x xe e = Lets [(x,xe)] e
single x = List [x]
@@ -113,7 +116,8 @@ instance Pretty Exp where
Op e1 op e2 -> hang (ppB e1<+>op) 2 (ppB e2)
Lets bs e -> sep ["let"<+>vcat [hang (x<+>"=") 2 xe|(x,xe)<-bs],
"in" <+>e]
LambdaCase alts -> hang "\\case" 4 (vcat [p<+>"->"<+>e|(p,e)<-alts])
LambdaCase alts ->
hang "\\case" 2 (vcat [hang (p<+>"->") 2 e|(p,e)<-alts])
_ -> ppB e
ppB e = case flatAp e of f:as -> hang (ppA f) 2 (sep (map ppA as))

View File

@@ -87,7 +87,10 @@ data Phase = Preproc | Convert | Compile | Link
deriving (Show,Eq,Ord)
data OutputFormat = FmtPGFPretty
| FmtCanonicalGF
| FmtCanonicalJson
| FmtJavaScript
| FmtJSON
| FmtPython
| FmtHaskell
| FmtJava
@@ -325,7 +328,8 @@ optDescr =
Option [] ["gfo-dir"] (ReqArg gfoDir "DIR") "Directory to put .gfo files in (default = '.').",
Option ['f'] ["output-format"] (ReqArg outFmt "FMT")
(unlines ["Output format. FMT can be one of:",
"Multiple concrete: pgf (default), js, pgf_pretty, prolog, python, ...", -- gar,
"Canonical GF grammar: canonical_gf, canonical_json, (and haskell with option --haskell=concrete)",
"Multiple concrete: pgf (default), json, js, pgf_pretty, prolog, python, ...", -- gar,
"Single concrete only: bnf, ebnf, fa, gsl, jsgf, regexp, slf, srgs_xml, srgs_abnf, vxml, ....", -- cf, lbnf,
"Abstract only: haskell, ..."]), -- prolog_abs,
Option [] ["sisr"] (ReqArg sisrFmt "FMT")
@@ -373,8 +377,6 @@ optDescr =
"Enable or disable global grammar optimization. This could significantly reduce the size of the final PGF file",
Option [] ["split-pgf"] (NoArg (splitPGF True))
"Split the PGF into one file per language. This allows the runtime to load only individual languages",
Option [] ["stem"] (onOff (toggleOptimize OptStem) True) "Perform stem-suffix analysis (default on).",
Option [] ["cse"] (onOff (toggleOptimize OptCSE) True) "Perform common sub-expression elimination (default on).",
Option [] ["cfg"] (ReqArg cfgTransform "TRANS") "Enable or disable specific CFG transformations. TRANS = merge, no-merge, bottomup, no-bottomup, ...",
Option [] ["heuristic_search_factor"] (ReqArg (readDouble (\d o -> o { optHeuristicFactor = Just d })) "FACTOR") "Set the heuristic search factor for statistical parsing",
Option [] ["case_sensitive"] (onOff (\v -> set $ \o -> o{optCaseSensitive=v}) True) "Set the parser in case-sensitive/insensitive mode [sensitive by default]",
@@ -448,8 +450,6 @@ optDescr =
optimize_pgf x = set $ \o -> o { optOptimizePGF = x }
splitPGF x = set $ \o -> o { optSplitPGF = x }
toggleOptimize x b = set $ setOptimization' x b
cfgTransform x = let (x', b) = case x of
'n':'o':'-':rest -> (rest, False)
_ -> (x, True)
@@ -472,7 +472,10 @@ outputFormats = map fst outputFormatsExpl
outputFormatsExpl :: [((String,OutputFormat),String)]
outputFormatsExpl =
[(("pgf_pretty", FmtPGFPretty),"human-readable pgf"),
(("canonical_gf", FmtCanonicalGF),"Canonical GF source files"),
(("canonical_json", FmtCanonicalJson),"Canonical JSON source files"),
(("js", FmtJavaScript),"JavaScript (whole grammar)"),
(("json", FmtJSON),"JSON (whole grammar)"),
(("python", FmtPython),"Python (whole grammar)"),
(("haskell", FmtHaskell),"Haskell (abstract syntax)"),
(("java", FmtJava),"Java (abstract syntax)"),

View File

@@ -23,7 +23,7 @@ import GF.System.Console (setConsoleEncoding)
-- Run @gf --help@ for usage info.
main :: IO ()
main = do
setConsoleEncoding
--setConsoleEncoding
uncurry mainOpts =<< getOptions
-- | Get and parse GF command line arguments. Fix relative paths.

View File

@@ -57,7 +57,7 @@ pgfToCFG pgf lang = mkCFG (showCId (lookStartCat pgf)) extCats (startRules ++ co
topdownRules cat = f cat []
where
f cat rules = maybe rules (Set.fold g rules) (IntMap.lookup cat (productions cnc))
f cat rules = maybe rules (Set.foldr g rules) (IntMap.lookup cat (productions cnc))
g (PApply funid args) rules = (cncfuns cnc ! funid,args) : rules
g (PCoerce cat) rules = f cat rules

View File

@@ -8,13 +8,13 @@ import System.Directory as D
doesDirectoryExist,doesFileExist,getModificationTime,
getCurrentDirectory,getDirectoryContents,getPermissions,
removeFile,renameFile)
import Data.Time.Compat
--import Data.Time.Compat
canonicalizePath path = liftIO $ D.canonicalizePath path
createDirectoryIfMissing b = liftIO . D.createDirectoryIfMissing b
doesDirectoryExist path = liftIO $ D.doesDirectoryExist path
doesFileExist path = liftIO $ D.doesFileExist path
getModificationTime path = liftIO $ fmap toUTCTime (D.getModificationTime path)
getModificationTime path = liftIO $ {-fmap toUTCTime-} (D.getModificationTime path)
getDirectoryContents path = liftIO $ D.getDirectoryContents path
getCurrentDirectory :: MonadIO io => io FilePath

View File

@@ -20,6 +20,7 @@ instance Pretty a => Pretty [a] where
ppList = fsep . map pp -- hmm
render x = PP.render (pp x)
render80 x = renderStyle style{lineLength=80,ribbonsPerLine=1} x
renderStyle s x = PP.renderStyle s (pp x)
infixl 5 $$,$+$

View File

@@ -1,489 +0,0 @@
{-# LANGUAGE FlexibleInstances, FlexibleContexts #-}
-- | This is a layer on top of "Data.Binary" with its own 'Binary' class
-- and customised instances for 'Word', 'Int' and 'Double'.
-- The 'Int' and 'Word' instance use a variable-length encoding to save space
-- for small numbers. The 'Double' instance uses the standard IEEE754 encoding.
module PGF.Data.Binary (
-- * The Binary class
Binary(..)
-- * The Get and Put monads
, Get , Put, runPut
-- * Useful helpers for writing instances
, putWord8 , getWord8 , putWord16be , getWord16be
-- * Binary serialisation
, encode , decode
-- * IO functions for serialisation
, encodeFile , decodeFile
, encodeFile_ , decodeFile_
-- * Useful
, Word8, Word16
) where
import Data.Word
import qualified Data.Binary as Bin
import Data.Binary.Put
import Data.Binary.Get
import Data.Binary.IEEE754 ( putFloat64be, getFloat64be)
import Control.Monad
import Control.Exception
import Foreign
import System.IO
import Data.ByteString.Lazy (ByteString)
import qualified Data.ByteString.Lazy as L
--import Data.Char (chr,ord)
--import Data.List (unfoldr)
-- And needed for the instances:
import qualified Data.ByteString as B
import qualified Data.Map as Map
import qualified Data.Set as Set
import qualified Data.IntMap as IntMap
import qualified Data.IntSet as IntSet
--import qualified Data.Ratio as R
--import qualified Data.Tree as T
import Data.Array.Unboxed
------------------------------------------------------------------------
-- | The @Binary@ class provides 'put' and 'get', methods to encode and
-- decode a Haskell value to a lazy ByteString. It mirrors the Read and
-- Show classes for textual representation of Haskell types, and is
-- suitable for serialising Haskell values to disk, over the network.
--
-- For parsing and generating simple external binary formats (e.g. C
-- structures), Binary may be used, but in general is not suitable
-- for complex protocols. Instead use the Put and Get primitives
-- directly.
--
-- Instances of Binary should satisfy the following property:
--
-- > decode . encode == id
--
-- That is, the 'get' and 'put' methods should be the inverse of each
-- other. A range of instances are provided for basic Haskell types.
--
class Binary t where
-- | Encode a value in the Put monad.
put :: t -> Put
-- | Decode a value in the Get monad
get :: Get t
------------------------------------------------------------------------
-- Wrappers to run the underlying monad
-- | Encode a value using binary serialisation to a lazy ByteString.
--
encode :: Binary a => a -> ByteString
encode = runPut . put
{-# INLINE encode #-}
-- | Decode a value from a lazy ByteString, reconstructing the original structure.
--
decode :: Binary a => ByteString -> a
decode = runGet get
------------------------------------------------------------------------
-- Convenience IO operations
-- | Lazily serialise a value to a file
--
-- This is just a convenience function, it's defined simply as:
--
-- > encodeFile f = B.writeFile f . encode
--
-- So for example if you wanted to compress as well, you could use:
--
-- > B.writeFile f . compress . encode
--
encodeFile :: Binary a => FilePath -> a -> IO ()
encodeFile f v = L.writeFile f (encode v)
encodeFile_ :: FilePath -> Put -> IO ()
encodeFile_ f m = L.writeFile f (runPut m)
-- | Lazily reconstruct a value previously written to a file.
--
-- This is just a convenience function, it's defined simply as:
--
-- > decodeFile f = return . decode =<< B.readFile f
--
-- So for example if you wanted to decompress as well, you could use:
--
-- > return . decode . decompress =<< B.readFile f
--
decodeFile :: Binary a => FilePath -> IO a
decodeFile f = bracket (openBinaryFile f ReadMode) hClose $ \h -> do
s <- L.hGetContents h
evaluate $ runGet get s
decodeFile_ :: FilePath -> Get a -> IO a
decodeFile_ f m = bracket (openBinaryFile f ReadMode) hClose $ \h -> do
s <- L.hGetContents h
evaluate $ runGet m s
------------------------------------------------------------------------
-- For ground types, the standard instances can be reused,
-- but for container types it would imply using
-- the standard instances for all types of values in the container...
instance Binary () where put=Bin.put; get=Bin.get
instance Binary Bool where put=Bin.put; get=Bin.get
instance Binary Word8 where put=Bin.put; get=Bin.get
instance Binary Word16 where put=Bin.put; get=Bin.get
instance Binary Char where put=Bin.put; get=Bin.get
-- -- GF doesn't need these:
--instance Binary Ordering where put=Bin.put; get=Bin.get
--instance Binary Word32 where put=Bin.put; get=Bin.get
--instance Binary Word64 where put=Bin.put; get=Bin.get
--instance Binary Int8 where put=Bin.put; get=Bin.get
--instance Binary Int16 where put=Bin.put; get=Bin.get
--instance Binary Int32 where put=Bin.put; get=Bin.get
--instance Binary Int64 where put=Bin.put; get=Bin.get -- needed by instance Binary ByteString
------------------------------------------------------------------------
-- Words are written as sequence of bytes. The last bit of each
-- byte indicates whether there are more bytes to be read
instance Binary Word where
put i | i <= 0x7f = do put a
| i <= 0x3fff = do put (a .|. 0x80)
put b
| i <= 0x1fffff = do put (a .|. 0x80)
put (b .|. 0x80)
put c
| i <= 0xfffffff = do put (a .|. 0x80)
put (b .|. 0x80)
put (c .|. 0x80)
put d
-- -- #if WORD_SIZE_IN_BITS < 64
| otherwise = do put (a .|. 0x80)
put (b .|. 0x80)
put (c .|. 0x80)
put (d .|. 0x80)
put e
{-
-- Restricted to 32 bits even on 64-bit systems, so that negative
-- Ints are written as 5 bytes instead of 10 bytes (TH 2013-02-13)
--#else
| i <= 0x7ffffffff = do put (a .|. 0x80)
put (b .|. 0x80)
put (c .|. 0x80)
put (d .|. 0x80)
put e
| i <= 0x3ffffffffff = do put (a .|. 0x80)
put (b .|. 0x80)
put (c .|. 0x80)
put (d .|. 0x80)
put (e .|. 0x80)
put f
| i <= 0x1ffffffffffff = do put (a .|. 0x80)
put (b .|. 0x80)
put (c .|. 0x80)
put (d .|. 0x80)
put (e .|. 0x80)
put (f .|. 0x80)
put g
| i <= 0xffffffffffffff = do put (a .|. 0x80)
put (b .|. 0x80)
put (c .|. 0x80)
put (d .|. 0x80)
put (e .|. 0x80)
put (f .|. 0x80)
put (g .|. 0x80)
put h
| i <= 0xffffffffffffff = do put (a .|. 0x80)
put (b .|. 0x80)
put (c .|. 0x80)
put (d .|. 0x80)
put (e .|. 0x80)
put (f .|. 0x80)
put (g .|. 0x80)
put h
| i <= 0x7fffffffffffffff = do put (a .|. 0x80)
put (b .|. 0x80)
put (c .|. 0x80)
put (d .|. 0x80)
put (e .|. 0x80)
put (f .|. 0x80)
put (g .|. 0x80)
put (h .|. 0x80)
put j
| otherwise = do put (a .|. 0x80)
put (b .|. 0x80)
put (c .|. 0x80)
put (d .|. 0x80)
put (e .|. 0x80)
put (f .|. 0x80)
put (g .|. 0x80)
put (h .|. 0x80)
put (j .|. 0x80)
put k
-- #endif
-}
where
a = fromIntegral ( i .&. 0x7f) :: Word8
b = fromIntegral (shiftR i 7 .&. 0x7f) :: Word8
c = fromIntegral (shiftR i 14 .&. 0x7f) :: Word8
d = fromIntegral (shiftR i 21 .&. 0x7f) :: Word8
e = fromIntegral (shiftR i 28 .&. 0x7f) :: Word8
{-
f = fromIntegral (shiftR i 35 .&. 0x7f) :: Word8
g = fromIntegral (shiftR i 42 .&. 0x7f) :: Word8
h = fromIntegral (shiftR i 49 .&. 0x7f) :: Word8
j = fromIntegral (shiftR i 56 .&. 0x7f) :: Word8
k = fromIntegral (shiftR i 63 .&. 0x7f) :: Word8
-}
get = do i <- getWord8
(if i <= 0x7f
then return (fromIntegral i)
else do n <- get
return $ (n `shiftL` 7) .|. (fromIntegral (i .&. 0x7f)))
-- Int has the same representation as Word
instance Binary Int where
put i = put (fromIntegral i :: Word)
get = liftM toInt32 (get :: Get Word)
where
-- restrict to 32 bits (for PGF portability, TH 2013-02-13)
toInt32 w = fromIntegral (fromIntegral w::Int32)::Int
------------------------------------------------------------------------
--
-- Portable, and pretty efficient, serialisation of Integer
--
-- Fixed-size type for a subset of Integer
--type SmallInt = Int32
-- Integers are encoded in two ways: if they fit inside a SmallInt,
-- they're written as a byte tag, and that value. If the Integer value
-- is too large to fit in a SmallInt, it is written as a byte array,
-- along with a sign and length field.
{-
instance Binary Integer where
{-# INLINE put #-}
put n | n >= lo && n <= hi = do
putWord8 0
put (fromIntegral n :: SmallInt) -- fast path
where
lo = fromIntegral (minBound :: SmallInt) :: Integer
hi = fromIntegral (maxBound :: SmallInt) :: Integer
put n = do
putWord8 1
put sign
put (unroll (abs n)) -- unroll the bytes
where
sign = fromIntegral (signum n) :: Word8
{-# INLINE get #-}
get = do
tag <- get :: Get Word8
case tag of
0 -> liftM fromIntegral (get :: Get SmallInt)
_ -> do sign <- get
bytes <- get
let v = roll bytes
return $! if sign == (1 :: Word8) then v else - v
--
-- Fold and unfold an Integer to and from a list of its bytes
--
unroll :: Integer -> [Word8]
unroll = unfoldr step
where
step 0 = Nothing
step i = Just (fromIntegral i, i `shiftR` 8)
roll :: [Word8] -> Integer
roll = foldr unstep 0
where
unstep b a = a `shiftL` 8 .|. fromIntegral b
instance (Binary a,Integral a) => Binary (R.Ratio a) where
put r = put (R.numerator r) >> put (R.denominator r)
get = liftM2 (R.%) get get
-}
------------------------------------------------------------------------
-- Instances for the first few tuples
instance (Binary a, Binary b) => Binary (a,b) where
put (a,b) = put a >> put b
get = liftM2 (,) get get
instance (Binary a, Binary b, Binary c) => Binary (a,b,c) where
put (a,b,c) = put a >> put b >> put c
get = liftM3 (,,) get get get
instance (Binary a, Binary b, Binary c, Binary d) => Binary (a,b,c,d) where
put (a,b,c,d) = put a >> put b >> put c >> put d
get = liftM4 (,,,) get get get get
instance (Binary a, Binary b, Binary c, Binary d, Binary e) => Binary (a,b,c,d,e) where
put (a,b,c,d,e) = put a >> put b >> put c >> put d >> put e
get = liftM5 (,,,,) get get get get get
--
-- and now just recurse:
--
instance (Binary a, Binary b, Binary c, Binary d, Binary e, Binary f)
=> Binary (a,b,c,d,e,f) where
put (a,b,c,d,e,f) = put (a,(b,c,d,e,f))
get = do (a,(b,c,d,e,f)) <- get ; return (a,b,c,d,e,f)
instance (Binary a, Binary b, Binary c, Binary d, Binary e, Binary f, Binary g)
=> Binary (a,b,c,d,e,f,g) where
put (a,b,c,d,e,f,g) = put (a,(b,c,d,e,f,g))
get = do (a,(b,c,d,e,f,g)) <- get ; return (a,b,c,d,e,f,g)
instance (Binary a, Binary b, Binary c, Binary d, Binary e,
Binary f, Binary g, Binary h)
=> Binary (a,b,c,d,e,f,g,h) where
put (a,b,c,d,e,f,g,h) = put (a,(b,c,d,e,f,g,h))
get = do (a,(b,c,d,e,f,g,h)) <- get ; return (a,b,c,d,e,f,g,h)
instance (Binary a, Binary b, Binary c, Binary d, Binary e,
Binary f, Binary g, Binary h, Binary i)
=> Binary (a,b,c,d,e,f,g,h,i) where
put (a,b,c,d,e,f,g,h,i) = put (a,(b,c,d,e,f,g,h,i))
get = do (a,(b,c,d,e,f,g,h,i)) <- get ; return (a,b,c,d,e,f,g,h,i)
instance (Binary a, Binary b, Binary c, Binary d, Binary e,
Binary f, Binary g, Binary h, Binary i, Binary j)
=> Binary (a,b,c,d,e,f,g,h,i,j) where
put (a,b,c,d,e,f,g,h,i,j) = put (a,(b,c,d,e,f,g,h,i,j))
get = do (a,(b,c,d,e,f,g,h,i,j)) <- get ; return (a,b,c,d,e,f,g,h,i,j)
------------------------------------------------------------------------
-- Container types
instance Binary a => Binary [a] where
put l = put (length l) >> mapM_ put l
get = do n <- get :: Get Int
xs <- replicateM n get
return xs
instance (Binary a) => Binary (Maybe a) where
put Nothing = putWord8 0
put (Just x) = putWord8 1 >> put x
get = do
w <- getWord8
case w of
0 -> return Nothing
_ -> liftM Just get
instance (Binary a, Binary b) => Binary (Either a b) where
put (Left a) = putWord8 0 >> put a
put (Right b) = putWord8 1 >> put b
get = do
w <- getWord8
case w of
0 -> liftM Left get
_ -> liftM Right get
------------------------------------------------------------------------
-- ByteStrings (have specially efficient instances)
instance Binary B.ByteString where
put bs = do put (B.length bs)
putByteString bs
get = get >>= getByteString
--
-- Using old versions of fps, this is a type synonym, and non portable
--
-- Requires 'flexible instances'
--
{-
instance Binary ByteString where
put bs = do put (fromIntegral (L.length bs) :: Int)
putLazyByteString bs
get = get >>= getLazyByteString
-}
------------------------------------------------------------------------
-- Maps and Sets
instance (Ord a, Binary a) => Binary (Set.Set a) where
put s = put (Set.size s) >> mapM_ put (Set.toAscList s)
get = liftM Set.fromDistinctAscList get
instance (Ord k, Binary k, Binary e) => Binary (Map.Map k e) where
put m = put (Map.size m) >> mapM_ put (Map.toAscList m)
get = liftM Map.fromDistinctAscList get
instance Binary IntSet.IntSet where
put s = put (IntSet.size s) >> mapM_ put (IntSet.toAscList s)
get = liftM IntSet.fromDistinctAscList get
instance (Binary e) => Binary (IntMap.IntMap e) where
put m = put (IntMap.size m) >> mapM_ put (IntMap.toAscList m)
get = liftM IntMap.fromDistinctAscList get
------------------------------------------------------------------------
-- Floating point
-- instance Binary Double where
-- put d = put (decodeFloat d)
-- get = liftM2 encodeFloat get get
instance Binary Double where
put = putFloat64be
get = getFloat64be
{-
instance Binary Float where
put f = put (decodeFloat f)
get = liftM2 encodeFloat get get
-}
------------------------------------------------------------------------
-- Trees
{-
instance (Binary e) => Binary (T.Tree e) where
put (T.Node r s) = put r >> put s
get = liftM2 T.Node get get
-}
------------------------------------------------------------------------
-- Arrays
instance (Binary i, Ix i, Binary e) => Binary (Array i e) where
put a = do
put (bounds a)
put (rangeSize $ bounds a) -- write the length
mapM_ put (elems a) -- now the elems.
get = do
bs <- get
n <- get -- read the length
xs <- replicateM n get -- now the elems.
return (listArray bs xs)
--
-- The IArray UArray e constraint is non portable. Requires flexible instances
--
instance (Binary i, Ix i, Binary e, IArray UArray e) => Binary (UArray i e) where
put a = do
put (bounds a)
put (rangeSize $ bounds a) -- now write the length
mapM_ put (elems a)
get = do
bs <- get
n <- get
xs <- replicateM n get
return (listArray bs xs)

View File

@@ -1,27 +0,0 @@
name: pgf-binary
version: 0.5
cabal-version: >= 1.10
build-type: Simple
license: BSD3
--license-file: LICENSE
synopsis: Custom version of the binary-0.5 package for the PGF library
homepage: http://www.grammaticalframework.org/
--bug-reports: http://code.google.com/p/grammatical-framework/issues/list
maintainer: Thomas Hallgren
stability: provisional
category: Data, Parsing
tested-with: GHC==7.4.2, GHC==7.8.3
source-repository head
type: darcs
location: http://www.grammaticalframework.org/
Library
default-language: Haskell2010
build-depends: base >= 4.3 && <5, binary, data-binary-ieee754,
containers, array, bytestring
exposed-modules: PGF.Data.Binary
ghc-options: -fwarn-unused-imports -O2
extensions: FlexibleInstances, FlexibleContexts

View File

@@ -68,6 +68,7 @@ libpgf_la_SOURCES = \
pgf/data.h \
pgf/expr.c \
pgf/expr.h \
pgf/scanner.c \
pgf/parser.c \
pgf/lookup.c \
pgf/jit.c \

View File

@@ -74,6 +74,8 @@
#ifdef GU_ALIGNOF
# define gu_alignof GU_ALIGNOF
#elif defined(_MSC_VER)
# define gu_alignof __alignof
#else
# define gu_alignof(t_) \
((size_t)(offsetof(struct { char c_; t_ e_; }, e_)))
@@ -87,7 +89,7 @@
#define GU_COMMA ,
#define GU_ARRAY_LEN(t,a) (sizeof((const t[])a) / sizeof(t))
#define GU_ARRAY_LEN(a) (sizeof(a) / sizeof(a[0]))
#define GU_ID(...) __VA_ARGS__
@@ -193,9 +195,13 @@ typedef union {
void (*fp)();
} GuMaxAlign;
#if defined(_MSC_VER)
#include <malloc.h>
#define gu_alloca(N) alloca(N)
#else
#define gu_alloca(N) \
(((union { GuMaxAlign align_; uint8_t buf_[N]; }){{0}}).buf_)
#endif
// For Doxygen
#define GU_PRIVATE /** @private */

View File

@@ -8,6 +8,10 @@
#include <sys/mman.h>
#include <sys/stat.h>
#endif
#if defined(__MINGW32__) || defined(_MSC_VER)
#include <malloc.h>
#endif
#if !defined(_MSC_VER)
#include <unistd.h>
#endif
@@ -108,6 +112,39 @@ gu_mem_buf_alloc(size_t min_size, size_t* real_size_out)
return gu_mem_buf_realloc(NULL, min_size, real_size_out);
}
#if defined(__MINGW32__) || defined(_MSC_VER)
#include <windows.h>
static int
getpagesize()
{
SYSTEM_INFO system_info;
GetSystemInfo(&system_info);
return system_info.dwPageSize;
}
#endif
GU_API void*
gu_mem_page_alloc(size_t min_size, size_t* real_size_out)
{
size_t page_size = getpagesize();
size_t size = ((min_size + page_size - 1) / page_size) * page_size;
void *page = NULL;
#if defined(ANDROID)
if ((page = memalign(page_size, size)) == NULL) {
#elif defined(__MINGW32__) || defined(_MSC_VER)
if ((page = malloc(size)) == NULL) {
#else
if (posix_memalign(&page, page_size, size) != 0) {
#endif
gu_fatal("Memory allocation failed");
}
*real_size_out = size;
return page;
}
GU_API void
gu_mem_buf_free(void* buf)
{
@@ -132,6 +169,7 @@ struct GuFinalizerNode {
enum GuPoolType {
GU_POOL_HEAP,
GU_POOL_LOCAL,
GU_POOL_PAGE,
GU_POOL_MMAP
};
@@ -180,6 +218,16 @@ gu_new_pool(void)
return pool;
}
GU_API GuPool*
gu_new_page_pool(void)
{
size_t sz = GU_FLEX_SIZE(GuPool, init_buf, gu_mem_pool_initial_size);
uint8_t* buf = gu_mem_page_alloc(sz, &sz);
GuPool* pool = gu_init_pool(buf, sz);
pool->type = GU_POOL_PAGE;
return pool;
}
GU_API GuPool*
gu_mmap_pool(char* fpath, void* addr, size_t size, void**pptr)
{
@@ -238,7 +286,10 @@ gu_pool_expand(GuPool* pool, size_t req)
gu_mem_chunk_max_size));
gu_assert(real_req >= sizeof(GuMemChunk));
size_t size = 0;
GuMemChunk* chunk = gu_mem_buf_alloc(real_req, &size);
GuMemChunk* chunk =
(pool->type == GU_POOL_PAGE)
? gu_mem_page_alloc(real_req, &size)
: gu_mem_buf_alloc(real_req, &size);
chunk->next = pool->chunks;
pool->chunks = chunk;
pool->curr_buf = (uint8_t*) chunk;
@@ -309,6 +360,7 @@ gu_malloc_prefixed(GuPool* pool, size_t pre_align, size_t pre_size,
size_t full_size = gu_mem_advance(offsetof(GuMemChunk, data),
pre_align, pre_size, align, size);
if (full_size > gu_mem_max_shared_alloc &&
pool->type != GU_POOL_PAGE &&
pool->type != GU_POOL_MMAP) {
GuMemChunk* chunk = gu_mem_alloc(full_size);
chunk->next = pool->chunks;

View File

@@ -55,6 +55,11 @@ gu_local_pool_(uint8_t* init_buf, size_t sz);
* should not be used in the bodies of recursive functions.
*/
/// Create a pool where each chunk is corresponds to one or
/// more pages.
GU_API_DECL GuPool*
gu_new_page_pool(void);
/// Create a pool stored in a memory mapped file.
GU_API_DECL GuPool*
gu_mmap_pool(char* fpath, void* addr, size_t size, void**pptr);
@@ -198,6 +203,9 @@ gu_mem_buf_realloc(
size_t min_size,
size_t* real_size_out);
/// Allocate enough memory pages to contain min_size bytes.
GU_API_DECL void*
gu_mem_page_alloc(size_t min_size, size_t* real_size_out);
/// Free a memory buffer.
GU_API_DECL void

View File

@@ -100,6 +100,11 @@ gu_seq_free(GuSeq* seq)
gu_mem_buf_free(seq);
}
static void
gu_dummy_finalizer(GuFinalizer* self)
{
}
GU_API void
gu_buf_require(GuBuf* buf, size_t req_len)
{
@@ -109,7 +114,9 @@ gu_buf_require(GuBuf* buf, size_t req_len)
size_t req_size = sizeof(GuSeq) + buf->elem_size * req_len;
size_t real_size;
gu_require(buf->fin.fn != gu_dummy_finalizer);
if (buf->seq == NULL || buf->seq == gu_empty_seq()) {
buf->seq = gu_mem_buf_alloc(req_size, &real_size);
buf->seq->len = 0;
@@ -164,6 +171,24 @@ gu_buf_freeze(GuBuf* buf, GuPool* pool)
return seq;
}
GU_API void
gu_buf_evacuate(GuBuf* buf, GuPool* pool)
{
if (buf->seq != gu_empty_seq()) {
size_t len = gu_buf_length(buf);
GuSeq* seq = gu_make_seq(buf->elem_size, len, pool);
void* bufdata = gu_buf_data(buf);
void* seqdata = gu_seq_data(seq);
memcpy(seqdata, bufdata, buf->elem_size * len);
gu_mem_buf_free(buf->seq);
buf->seq = seq;
buf->fin.fn = gu_dummy_finalizer;
buf->avail_len = len;
}
}
GU_API void*
gu_buf_insert(GuBuf* buf, size_t index)
{
@@ -335,13 +360,8 @@ GU_API void
gu_buf_heap_pop(GuBuf *buf, GuOrder *order, void* data_out)
{
const void* last = gu_buf_trim(buf); // raises an error if empty
if (gu_buf_length(buf) > 0) {
memcpy(data_out, buf->seq->data, buf->elem_size);
gu_heap_siftup(buf, order, last, 0);
} else {
memcpy(data_out, last, buf->elem_size);
}
memcpy(data_out, buf->seq->data, buf->elem_size);
gu_heap_siftup(buf, order, last, 0);
}
GU_API void

View File

@@ -182,6 +182,9 @@ gu_buf_heapify(GuBuf *buf, GuOrder *order);
GU_API_DECL GuSeq*
gu_buf_freeze(GuBuf* buf, GuPool* pool);
GU_API_DECL void
gu_buf_evacuate(GuBuf* buf, GuPool* pool);
#endif // GU_SEQ_H_
#ifdef GU_STRING_H_

View File

@@ -197,16 +197,16 @@ pgf_literal_hash(GuHash h, PgfLiteral lit);
PGF_API_DECL GuHash
pgf_expr_hash(GuHash h, PgfExpr e);
PGF_API size_t
PGF_API_DECL size_t
pgf_expr_size(PgfExpr expr);
PGF_API GuSeq*
PGF_API_DECL GuSeq*
pgf_expr_functions(PgfExpr expr, GuPool* pool);
PGF_API PgfExpr
PGF_API_DECL PgfExpr
pgf_expr_substitute(PgfExpr expr, GuSeq* meta_values, GuPool* pool);
PGF_API PgfType*
PGF_API_DECL PgfType*
pgf_type_substitute(PgfType* type, GuSeq* meta_values, GuPool* pool);
typedef struct PgfPrintContext PgfPrintContext;

View File

@@ -5,9 +5,6 @@
#include <pgf/reasoner.h>
#include <pgf/reader.h>
#include "lightning.h"
#if defined(__MINGW32__) || defined(_MSC_VER)
#include <malloc.h>
#endif
//#define PGF_JIT_DEBUG
@@ -43,18 +40,6 @@ typedef struct {
#define JIT_VSTATE JIT_V1
#define JIT_VCLOS JIT_V2
#if defined(__MINGW32__) || defined(_MSC_VER)
#include <windows.h>
static int
getpagesize()
{
SYSTEM_INFO system_info;
GetSystemInfo(&system_info);
return system_info.dwPageSize;
}
#endif
static void
pgf_jit_finalize_page(GuFinalizer* self)
@@ -65,19 +50,8 @@ pgf_jit_finalize_page(GuFinalizer* self)
static void
pgf_jit_alloc_page(PgfReader* rdr)
{
void *page;
size_t page_size = getpagesize();
#if defined(ANDROID)
if ((page = memalign(page_size, page_size)) == NULL) {
#elif defined(__MINGW32__) || defined(_MSC_VER)
if ((page = malloc(page_size)) == NULL) {
#else
if (posix_memalign(&page, page_size, page_size) != 0) {
#endif
gu_fatal("Memory allocation failed");
}
size_t page_size;
void *page = gu_mem_page_alloc(sizeof(GuFinalizer), &page_size);
GuFinalizer* fin = page;
fin->fn = pgf_jit_finalize_page;

File diff suppressed because it is too large Load Diff

View File

@@ -167,6 +167,22 @@ PGF_API_DECL void
pgf_lookup_morpho(PgfConcr *concr, GuString sentence,
PgfMorphoCallback* callback, GuExn* err);
typedef struct {
size_t pos;
GuString ptr;
} PgfCohortSpot;
typedef struct {
PgfCohortSpot start;
PgfCohortSpot end;
GuBuf* buf;
} PgfCohortRange;
PGF_API_DECL GuEnum*
pgf_lookup_cohorts(PgfConcr *concr, GuString sentence,
PgfMorphoCallback* callback,
GuPool* pool, GuExn* err);
typedef struct PgfFullFormEntry PgfFullFormEntry;
PGF_API_DECL GuEnum*

View File

@@ -94,6 +94,74 @@ pgf_print_fid(int fid, GuOut* out, GuExn* err)
gu_printf(out, err, "C%d", fid);
}
PGF_INTERNAL void
pgf_print_production_args(PgfPArgs* args,
GuOut* out, GuExn* err)
{
size_t n_args = gu_seq_length(args);
for (size_t j = 0; j < n_args; j++) {
if (j > 0)
gu_putc(',',out,err);
PgfPArg arg = gu_seq_get(args, PgfPArg, j);
if (arg.hypos != NULL &&
gu_seq_length(arg.hypos) > 0) {
size_t n_hypos = gu_seq_length(arg.hypos);
for (size_t k = 0; k < n_hypos; k++) {
PgfCCat *hypo = gu_seq_get(arg.hypos, PgfCCat*, k);
pgf_print_fid(hypo->fid, out, err);
gu_putc(' ',out,err);
}
gu_puts("-> ",out,err);
}
pgf_print_fid(arg.ccat->fid, out, err);
}
}
PGF_INTERNAL void
pgf_print_production(int fid, PgfProduction prod,
GuOut *out, GuExn* err)
{
pgf_print_fid(fid, out, err);
gu_puts(" -> ", out, err);
GuVariantInfo i = gu_variant_open(prod);
switch (i.tag) {
case PGF_PRODUCTION_APPLY: {
PgfProductionApply* papp = i.data;
gu_printf(out,err,"F%d(",papp->fun->funid);
if (papp->fun->ep != NULL) {
pgf_print_expr(papp->fun->ep->expr, NULL, 0, out, err);
} else {
PgfPArg* parg = gu_seq_index(papp->args, PgfPArg, 0);
gu_printf(out,err,"linref %s", parg->ccat->cnccat->abscat->name);
}
gu_printf(out,err,")[");
pgf_print_production_args(papp->args,out,err);
gu_printf(out,err,"]\n");
break;
}
case PGF_PRODUCTION_COERCE: {
PgfProductionCoerce* pcoerce = i.data;
gu_puts("_[",out,err);
pgf_print_fid(pcoerce->coerce->fid, out, err);
gu_puts("]\n",out,err);
break;
}
case PGF_PRODUCTION_EXTERN: {
PgfProductionExtern* pext = i.data;
gu_printf(out,err,"<extern>(");
pgf_print_expr(pext->ep->expr, NULL, 0, out, err);
gu_printf(out,err,")[]\n");
break;
}
default:
gu_impossible();
}
}
static void
pgf_print_productions(GuMapItor* fn, const void* key, void* value,
GuExn* err)
@@ -107,48 +175,7 @@ pgf_print_productions(GuMapItor* fn, const void* key, void* value,
size_t n_prods = gu_seq_length(ccat->prods);
for (size_t i = 0; i < n_prods; i++) {
PgfProduction prod = gu_seq_get(ccat->prods, PgfProduction, i);
gu_puts(" ", out, err);
pgf_print_fid(fid, out, err);
gu_puts(" -> ", out, err);
GuVariantInfo i = gu_variant_open(prod);
switch (i.tag) {
case PGF_PRODUCTION_APPLY: {
PgfProductionApply* papp = i.data;
gu_printf(out,err,"F%d[",papp->fun->funid);
size_t n_args = gu_seq_length(papp->args);
for (size_t j = 0; j < n_args; j++) {
if (j > 0)
gu_putc(',',out,err);
PgfPArg arg = gu_seq_get(papp->args, PgfPArg, j);
if (arg.hypos != NULL) {
size_t n_hypos = gu_seq_length(arg.hypos);
for (size_t k = 0; k < n_hypos; k++) {
if (k > 0)
gu_putc(' ',out,err);
PgfCCat *hypo = gu_seq_get(arg.hypos, PgfCCat*, k);
pgf_print_fid(hypo->fid, out, err);
}
}
pgf_print_fid(arg.ccat->fid, out, err);
}
gu_printf(out,err,"]\n");
break;
}
case PGF_PRODUCTION_COERCE: {
PgfProductionCoerce* pcoerce = i.data;
gu_puts("_[", out, err);
pgf_print_fid(pcoerce->coerce->fid, out, err);
gu_puts("]\n", out, err);
break;
}
default:
gu_impossible();
}
pgf_print_production(fid, prod, out, err);
}
}
}

View File

@@ -328,16 +328,20 @@ pgf_read_patt(PgfReader* rdr)
uint8_t tag = pgf_read_tag(rdr);
switch (tag) {
case PGF_PATT_APP: {
PgfCId ctor = pgf_read_cid(rdr, rdr->opool);
gu_return_on_exn(rdr->err, gu_null_variant);
size_t n_args = pgf_read_len(rdr);
gu_return_on_exn(rdr->err, gu_null_variant);
PgfPattApp *papp =
gu_new_variant(PGF_PATT_APP,
PgfPattApp,
&patt, rdr->opool);
papp->ctor = pgf_read_cid(rdr, rdr->opool);
gu_return_on_exn(rdr->err, gu_null_variant);
papp->n_args = pgf_read_len(rdr);
gu_return_on_exn(rdr->err, gu_null_variant);
gu_new_flex_variant(PGF_PATT_APP,
PgfPattApp,
args, n_args,
&patt, rdr->opool);
papp->ctor = ctor;
papp->n_args = n_args;
for (size_t i = 0; i < papp->n_args; i++) {
papp->args[i] = pgf_read_patt(rdr);
gu_return_on_exn(rdr->err, gu_null_variant);

516
src/runtime/c/pgf/scanner.c Normal file
View File

@@ -0,0 +1,516 @@
#include <pgf/data.h>
#include <pgf/expr.h>
#include <pgf/linearizer.h>
#include <gu/utf8.h>
PGF_INTERNAL int
cmp_string(PgfCohortSpot* spot, GuString tok,
bool case_sensitive)
{
for (;;) {
GuUCS c2 = gu_utf8_decode((const uint8_t**) &tok);
if (c2 == 0)
return 0;
const uint8_t* p = (uint8_t*) spot->ptr;
GuUCS c1 = gu_utf8_decode(&p);
if (c1 == 0)
return -1;
if (!case_sensitive) {
c1 = gu_ucs_to_lower(c1);
c2 = gu_ucs_to_lower(c2);
}
if (c1 != c2)
return (c1-c2);
spot->ptr = (GuString) p;
spot->pos++;
}
}
PGF_INTERNAL bool
skip_space(GuString* psent, size_t* ppos)
{
const uint8_t* p = (uint8_t*) *psent;
if (!gu_ucs_is_space(gu_utf8_decode(&p)))
return false;
*psent = (GuString) p;
(*ppos)++;
return true;
}
PGF_INTERNAL int
pgf_symbols_cmp(PgfCohortSpot* spot,
PgfSymbols* syms, size_t* sym_idx,
bool case_sensitive)
{
size_t n_syms = gu_seq_length(syms);
while (*sym_idx < n_syms) {
PgfSymbol sym = gu_seq_get(syms, PgfSymbol, *sym_idx);
if (*sym_idx > 0) {
if (!skip_space(&spot->ptr,&spot->pos)) {
if (*spot->ptr == 0)
return -1;
return 1;
}
while (*spot->ptr != 0) {
if (!skip_space(&spot->ptr,&spot->pos))
break;
}
}
GuVariantInfo inf = gu_variant_open(sym);
switch (inf.tag) {
case PGF_SYMBOL_CAT:
case PGF_SYMBOL_LIT:
case PGF_SYMBOL_VAR: {
if (*spot->ptr == 0)
return -1;
return 1;
}
case PGF_SYMBOL_KS: {
PgfSymbolKS* pks = inf.data;
if (*spot->ptr == 0)
return -1;
int cmp = cmp_string(spot,pks->token, case_sensitive);
if (cmp != 0)
return cmp;
break;
}
case PGF_SYMBOL_KP:
case PGF_SYMBOL_BIND:
case PGF_SYMBOL_NE:
case PGF_SYMBOL_SOFT_BIND:
case PGF_SYMBOL_SOFT_SPACE:
case PGF_SYMBOL_CAPIT:
case PGF_SYMBOL_ALL_CAPIT: {
return -1;
}
default:
gu_impossible();
}
(*sym_idx)++;
}
return 0;
}
static void
pgf_morpho_iter(PgfProductionIdx* idx,
PgfMorphoCallback* callback,
GuExn* err)
{
size_t n_entries = gu_buf_length(idx);
for (size_t i = 0; i < n_entries; i++) {
PgfProductionIdxEntry* entry =
gu_buf_index(idx, PgfProductionIdxEntry, i);
PgfCId lemma = entry->papp->fun->absfun->name;
GuString analysis = entry->ccat->cnccat->labels[entry->lin_idx];
prob_t prob = entry->ccat->cnccat->abscat->prob +
entry->papp->fun->absfun->ep.prob;
callback->callback(callback,
lemma, analysis, prob, err);
if (!gu_ok(err))
return;
}
}
typedef struct {
GuOrder order;
bool case_sensitive;
} PgfSequenceOrder;
PGF_INTERNAL bool
pgf_is_case_sensitive(PgfConcr* concr)
{
PgfFlag* flag =
gu_seq_binsearch(concr->cflags, pgf_flag_order, PgfFlag, "case_sensitive");
if (flag != NULL) {
GuVariantInfo inf = gu_variant_open(flag->value);
if (inf.tag == PGF_LITERAL_STR) {
PgfLiteralStr* lstr = inf.data;
if (strcmp(lstr->val, "off") == 0)
return false;
}
}
return true;
}
static int
pgf_sequence_cmp_fn(GuOrder* order, const void* p1, const void* p2)
{
PgfSequenceOrder* self = gu_container(order, PgfSequenceOrder, order);
PgfCohortSpot spot = {0, (GuString) p1};
const PgfSequence* sp2 = p2;
size_t sym_idx = 0;
int res = pgf_symbols_cmp(&spot, sp2->syms, &sym_idx, self->case_sensitive);
if (res == 0 && (*spot.ptr != 0 || sym_idx != gu_seq_length(sp2->syms))) {
res = 1;
}
return res;
}
PGF_API void
pgf_lookup_morpho(PgfConcr *concr, GuString sentence,
PgfMorphoCallback* callback, GuExn* err)
{
if (concr->sequences == NULL) {
GuExnData* err_data = gu_raise(err, PgfExn);
if (err_data) {
err_data->data = "The concrete syntax is not loaded";
return;
}
}
size_t index = 0;
PgfSequenceOrder order = { { pgf_sequence_cmp_fn },
pgf_is_case_sensitive(concr) };
if (gu_seq_binsearch_index(concr->sequences, &order.order,
PgfSequence, (void*) sentence,
&index)) {
PgfSequence* seq = NULL;
/* If the match is case-insensitive then there might be more
* matches around the current index. We must check the neighbour
* sequences for matching as well.
*/
if (!order.case_sensitive) {
size_t i = index;
while (i > 0) {
seq = gu_seq_index(concr->sequences, PgfSequence, i-1);
size_t sym_idx = 0;
PgfCohortSpot spot = {0, sentence};
if (pgf_symbols_cmp(&spot, seq->syms, &sym_idx, order.case_sensitive) != 0) {
break;
}
if (seq->idx != NULL)
pgf_morpho_iter(seq->idx, callback, err);
i--;
}
}
seq = gu_seq_index(concr->sequences, PgfSequence, index);
if (seq->idx != NULL)
pgf_morpho_iter(seq->idx, callback, err);
if (!order.case_sensitive) {
size_t i = index+1;
while (i < gu_seq_length(concr->sequences)) {
seq = gu_seq_index(concr->sequences, PgfSequence, i);
size_t sym_idx = 0;
PgfCohortSpot spot = {0, sentence};
if (pgf_symbols_cmp(&spot, seq->syms, &sym_idx, order.case_sensitive) != 0) {
break;
}
if (seq->idx != NULL)
pgf_morpho_iter(seq->idx, callback, err);
i++;
}
}
}
}
typedef struct {
GuEnum en;
PgfConcr* concr;
GuString sentence;
GuString current;
size_t len;
PgfMorphoCallback* callback;
GuExn* err;
bool case_sensitive;
GuBuf* spots;
GuBuf* found;
} PgfCohortsState;
static int
cmp_cohort_spot(GuOrder* self, const void* a, const void* b)
{
PgfCohortSpot *s1 = (PgfCohortSpot *) a;
PgfCohortSpot *s2 = (PgfCohortSpot *) b;
return (s1->ptr-s2->ptr);
}
static GuOrder
pgf_cohort_spot_order[1] = {{ cmp_cohort_spot }};
static void
pgf_lookup_cohorts_helper(PgfCohortsState *state, PgfCohortSpot* spot,
int i, int j, ptrdiff_t min, ptrdiff_t max)
{
// This is a variation of a binary search algorithm which
// can retrieve all prefixes of a string with minimal
// comparisons, i.e. there is no need to lookup every
// prefix separately.
while (i <= j) {
int k = (i+j) / 2;
PgfSequence* seq = gu_seq_index(state->concr->sequences, PgfSequence, k);
PgfCohortSpot current = *spot;
size_t sym_idx = 0;
int cmp = pgf_symbols_cmp(&current, seq->syms, &sym_idx, state->case_sensitive);
if (cmp < 0) {
j = k-1;
} else if (cmp > 0) {
ptrdiff_t len = current.ptr - spot->ptr;
if (min <= len)
pgf_lookup_cohorts_helper(state, spot, i, k-1, min, len);
if (len+1 <= max)
pgf_lookup_cohorts_helper(state, spot, k+1, j, len+1, max);
break;
} else {
ptrdiff_t len = current.ptr - spot->ptr;
if (min <= len)
pgf_lookup_cohorts_helper(state, spot, i, k-1, min, len);
if (seq->idx != NULL && gu_buf_length(seq->idx) > 0) {
PgfCohortRange* range = gu_buf_insert(state->found, 0);
range->start = *spot;
range->end = current;
range->buf = seq->idx;
}
while (*current.ptr != 0) {
if (!skip_space(&current.ptr, &current.pos))
break;
}
gu_buf_heap_push(state->spots, pgf_cohort_spot_order, &current);
if (len <= max)
pgf_lookup_cohorts_helper(state, spot, k+1, j, len, max);
break;
}
}
}
static void
pgf_lookup_cohorts_enum_next(GuEnum* self, void* to, GuPool* pool)
{
PgfCohortsState* state = gu_container(self, PgfCohortsState, en);
while (gu_buf_length(state->found) == 0 &&
gu_buf_length(state->spots) > 0) {
PgfCohortSpot spot;
gu_buf_heap_pop(state->spots, pgf_cohort_spot_order, &spot);
if (spot.ptr == state->current)
continue;
if (*spot.ptr == 0)
break;
pgf_lookup_cohorts_helper
(state, &spot,
0, gu_seq_length(state->concr->sequences)-1,
1, (state->sentence+state->len)-spot.ptr);
if (gu_buf_length(state->found) == 0) {
// skip one character and try again
gu_utf8_decode((const uint8_t**) &spot.ptr);
spot.pos++;
gu_buf_heap_push(state->spots, pgf_cohort_spot_order, &spot);
}
}
PgfCohortRange* pRes = (PgfCohortRange*)to;
if (gu_buf_length(state->found) == 0) {
pRes->start.pos = 0;
pRes->start.ptr = NULL;
pRes->end.pos = 0;
pRes->end.ptr = NULL;
pRes->buf = NULL;
state->current = NULL;
return;
} else do {
*pRes = gu_buf_pop(state->found, PgfCohortRange);
state->current = pRes->start.ptr;
pgf_morpho_iter(pRes->buf, state->callback, state->err);
} while (gu_buf_length(state->found) > 0 &&
gu_buf_index_last(state->found, PgfCohortRange)->end.ptr == pRes->end.ptr);
}
PGF_API GuEnum*
pgf_lookup_cohorts(PgfConcr *concr, GuString sentence,
PgfMorphoCallback* callback,
GuPool* pool, GuExn* err)
{
if (concr->sequences == NULL) {
GuExnData* err_data = gu_raise(err, PgfExn);
if (err_data) {
err_data->data = "The concrete syntax is not loaded";
return NULL;
}
}
PgfCohortsState* state = gu_new(PgfCohortsState, pool);
state->en.next = pgf_lookup_cohorts_enum_next;
state->concr = concr;
state->sentence= sentence;
state->len = strlen(sentence);
state->callback= callback;
state->err = err;
state->case_sensitive = pgf_is_case_sensitive(concr);
state->spots = gu_new_buf(PgfCohortSpot, pool);
state->found = gu_new_buf(PgfCohortRange, pool);
PgfCohortSpot spot = {0,sentence};
while (*spot.ptr != 0) {
if (!skip_space(&spot.ptr, &spot.pos))
break;
}
gu_buf_heap_push(state->spots, pgf_cohort_spot_order, &spot);
return &state->en;
}
typedef struct {
GuEnum en;
PgfSequences* sequences;
GuString prefix;
size_t seq_idx;
bool case_sensitive;
} PgfFullFormState;
struct PgfFullFormEntry {
GuString tokens;
PgfProductionIdx* idx;
};
static void
gu_fullform_enum_next(GuEnum* self, void* to, GuPool* pool)
{
PgfFullFormState* st = gu_container(self, PgfFullFormState, en);
PgfFullFormEntry* entry = NULL;
if (st->sequences != NULL) {
size_t n_seqs = gu_seq_length(st->sequences);
while (st->seq_idx < n_seqs) {
PgfSequence* seq = gu_seq_index(st->sequences, PgfSequence, st->seq_idx);
GuString tokens = pgf_get_tokens(seq->syms, 0, pool);
PgfCohortSpot spot = {0, st->prefix};
if (cmp_string(&spot, tokens, st->case_sensitive) > 0 || *spot.ptr != 0) {
st->seq_idx = n_seqs;
break;
}
if (*tokens != 0 && seq->idx != NULL) {
entry = gu_new(PgfFullFormEntry, pool);
entry->tokens = tokens;
entry->idx = seq->idx;
st->seq_idx++;
break;
}
st->seq_idx++;
}
}
*((PgfFullFormEntry**) to) = entry;
}
PGF_API GuEnum*
pgf_fullform_lexicon(PgfConcr *concr, GuPool* pool)
{
PgfFullFormState* st = gu_new(PgfFullFormState, pool);
st->en.next = gu_fullform_enum_next;
st->sequences = concr->sequences;
st->prefix = "";
st->seq_idx = 0;
st->case_sensitive = true;
return &st->en;
}
PGF_API GuString
pgf_fullform_get_string(PgfFullFormEntry* entry)
{
return entry->tokens;
}
PGF_API void
pgf_fullform_get_analyses(PgfFullFormEntry* entry,
PgfMorphoCallback* callback, GuExn* err)
{
pgf_morpho_iter(entry->idx, callback, err);
}
PGF_API GuEnum*
pgf_lookup_word_prefix(PgfConcr *concr, GuString prefix,
GuPool* pool, GuExn* err)
{
if (concr->sequences == NULL) {
GuExnData* err_data = gu_raise(err, PgfExn);
if (err_data) {
err_data->data = "The concrete syntax is not loaded";
return NULL;
}
}
PgfFullFormState* state = gu_new(PgfFullFormState, pool);
state->en.next = gu_fullform_enum_next;
state->sequences = concr->sequences;
state->prefix = prefix;
state->seq_idx = 0;
state->case_sensitive = pgf_is_case_sensitive(concr);
PgfSequenceOrder order = { { pgf_sequence_cmp_fn },
state->case_sensitive };
if (!gu_seq_binsearch_index(concr->sequences, &order.order,
PgfSequence, (void*) prefix,
&state->seq_idx)) {
state->seq_idx++;
} else if (!state->case_sensitive) {
/* If the match is case-insensitive then there might be more
* matches around the current index. Since we scroll down
* anyway, it is enough to search upwards now.
*/
while (state->seq_idx > 0) {
PgfSequence* seq =
gu_seq_index(concr->sequences, PgfSequence, state->seq_idx-1);
size_t sym_idx = 0;
PgfCohortSpot spot = {0, state->prefix};
if (pgf_symbols_cmp(&spot, seq->syms, &sym_idx, state->case_sensitive) > 0 || *spot.ptr != 0) {
break;
}
state->seq_idx--;
}
}
return &state->en;
}

View File

@@ -499,14 +499,17 @@ store_expr(SgSG* sg,
PgfExprLit* elit = ei.data;
Mem mem[2];
size_t len = 0;
GuVariantInfo li = gu_variant_open(elit->lit);
switch (li.tag) {
case PGF_LITERAL_STR: {
PgfLiteralStr* lstr = li.data;
len = strlen(lstr->val);
mem[0].flags = MEM_Str;
mem[0].n = strlen(lstr->val);
mem[0].n = len;
mem[0].z = lstr->val;
break;
}
@@ -515,6 +518,7 @@ store_expr(SgSG* sg,
mem[0].flags = MEM_Int;
mem[0].u.i = lint->val;
len = sizeof(mem[0].u.i);
break;
}
case PGF_LITERAL_FLT: {
@@ -522,6 +526,7 @@ store_expr(SgSG* sg,
mem[0].flags = MEM_Real;
mem[0].u.r = lflt->val;
len = sizeof(mem[0].u.r);
break;
}
default:
@@ -556,7 +561,7 @@ store_expr(SgSG* sg,
int serial_type_arg = sqlite3BtreeSerialType(&mem[1], file_format);
int serial_type_arg_hdr_len = sqlite3BtreeVarintLen(serial_type_arg);
unsigned char* buf = malloc(1+serial_type_lit_hdr_len+(serial_type_arg_hdr_len > 1 ? serial_type_arg_hdr_len : 1)+mem[0].n+8);
unsigned char* buf = malloc(1+serial_type_lit_hdr_len+(serial_type_arg_hdr_len > 1 ? serial_type_arg_hdr_len : 1)+len+8);
unsigned char* p = buf;
*p++ = 1+serial_type_lit_hdr_len+serial_type_arg_hdr_len;
p += putVarint32(p, serial_type_lit);

View File

@@ -4835,7 +4835,6 @@ SQLITE_PRIVATE int sqlite3HeaderSizeBtree(void);
SQLITE_PRIVATE void sqlite3VdbeRecordUnpack(KeyInfo*,int,const void*,UnpackedRecord*);
SQLITE_PRIVATE UnpackedRecord *sqlite3VdbeAllocUnpackedRecord(KeyInfo *, char *, int, char **);
typedef int (*RecordCompare)(int,const void*,UnpackedRecord*);
SQLITE_PRIVATE RecordCompare sqlite3VdbeFindCompare(UnpackedRecord*);
/************** End of btreeInt.h ********************************************/

View File

@@ -70,7 +70,7 @@ module PGF2 (-- * PGF
-- ** Generation
generateAll,
-- ** Morphological Analysis
MorphoAnalysis, lookupMorpho, fullFormLexicon,
MorphoAnalysis, lookupMorpho, lookupCohorts, fullFormLexicon,
-- ** Visualizations
GraphvizOptions(..), graphvizDefaults,
graphvizAbstractTree, graphvizParseTree, graphvizWordAlignment,
@@ -466,8 +466,23 @@ newGraphvizOptions pool opts = do
-- Functions using Concr
-- Morpho analyses, parsing & linearization
type MorphoAnalysis = (Fun,Cat,Float)
-- | This triple is returned by all functions that deal with
-- the grammar's lexicon. Its first element is the name of an abstract
-- lexical function which can produce a given word or
-- a multiword expression (i.e. this is the lemma).
-- After that follows a string which describes
-- the particular inflection form.
--
-- The last element is a logarithm from the
-- the probability of the function. The probability is not
-- conditionalized on the category of the function. This makes it
-- possible to compare the likelihood of two functions even if they
-- have different types.
type MorphoAnalysis = (Fun,String,Float)
-- | 'lookupMorpho' takes a string which must be a single word or
-- a multiword expression. It then computes the list of all possible
-- morphological analyses.
lookupMorpho :: Concr -> String -> [MorphoAnalysis]
lookupMorpho (Concr concr master) sent =
unsafePerformIO $
@@ -481,6 +496,45 @@ lookupMorpho (Concr concr master) sent =
freeHaskellFunPtr fptr
readIORef ref
-- | 'lookupCohorts' takes an arbitrary string an produces
-- a list of all places where lexical items from the grammar have been
-- identified (i.e. cohorts). The list consists of triples of the format @(start,ans,end)@,
-- where @start-end@ identifies the span in the text and @ans@ is
-- the list of possible morphological analyses similar to 'lookupMorpho'.
--
-- The list is sorted first by the @start@ position and after than
-- by the @end@ position. This can be used for instance if you want to
-- filter only the longest matches.
lookupCohorts :: Concr -> String -> [(Int,[MorphoAnalysis],Int)]
lookupCohorts lang@(Concr concr master) sent =
unsafePerformIO $
do pl <- gu_new_pool
ref <- newIORef []
cback <- gu_malloc pl (#size PgfMorphoCallback)
fptr <- wrapLookupMorphoCallback (getAnalysis ref)
(#poke PgfMorphoCallback, callback) cback fptr
c_sent <- newUtf8CString sent pl
enum <- pgf_lookup_cohorts concr c_sent cback pl nullPtr
fpl <- newForeignPtr gu_pool_finalizer pl
fromCohortRange enum fpl fptr ref
where
fromCohortRange enum fpl fptr ref =
allocaBytes (#size PgfCohortRange) $ \ptr ->
withForeignPtr fpl $ \pl ->
do gu_enum_next enum ptr pl
buf <- (#peek PgfCohortRange, buf) ptr
if buf == nullPtr
then do finalizeForeignPtr fpl
freeHaskellFunPtr fptr
touchConcr lang
return []
else do start <- (#peek PgfCohortRange, start.pos) ptr
end <- (#peek PgfCohortRange, end.pos) ptr
ans <- readIORef ref
writeIORef ref []
cohs <- unsafeInterleaveIO (fromCohortRange enum fpl fptr ref)
return ((start,ans,end):cohs)
fullFormLexicon :: Concr -> [(String, [MorphoAnalysis])]
fullFormLexicon lang =
unsafePerformIO $
@@ -990,11 +1044,13 @@ withBracketLinFuncs ref exn f =
end_phrase ref _ c_cat c_fid c_lindex c_fun = do
(bs':stack,bs) <- readIORef ref
cat <- peekUtf8CString c_cat
let fid = fromIntegral c_fid
let lindex = fromIntegral c_lindex
fun <- peekUtf8CString c_fun
writeIORef ref (stack, Bracket cat fid lindex fun (reverse bs) : bs')
if null bs
then writeIORef ref (stack, bs')
else do cat <- peekUtf8CString c_cat
let fid = fromIntegral c_fid
let lindex = fromIntegral c_lindex
fun <- peekUtf8CString c_fun
writeIORef ref (stack, Bracket cat fid lindex fun (reverse bs) : bs')
symbol_ne exn _ = do
gu_exn_raise exn gu_exn_type_PgfLinNonExist

Some files were not shown because too many files have changed in this diff Show More