Git Product home page Git Product logo

bnf-playground's People

Contributors

mikesamuel avatar paul-kline avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar

bnf-playground's Issues

Hugely useful tool

I'm using the tool to explore a new grammar, an adaptation of the PL/I language. The tool is extremely helpful and as I use it several things have come up on a "wish list" I'll list them here in case you get an opportunity to consider them.

The biggest limitation just now is that I can't paste a test input because it contains whitespaces and I don't know how to cater for that in a grammar. Ordinarily the lexical analyzer strips these away so we just see tokens but here there is no lexer as such.

Here's the gist of the grammar at an early stage, this is very draft and far from complete at this stage:

/* https://bnfplayground.pauliankline.com/ */

<DCL> ::= " dcl " | " declare "
<ARG> ::= " arg " | "argument "
<PROC> ::= " proc " | " procedure "
<FUNC> ::= " func " | " function "
<BIN>  ::= " bin " | " binary "
<DEC> ::= " dec " | "decimal "
<STRING> ::= " string "
<STATIC> ::= " static "
<BASED> ::= " based "
<CALL> ::= " call "
<GOTO> ::= " goto " | " go to "
<RETURN> ::= " return " 
<RETURNTO> ::= " return to "
<IF> ::= " if "
<THEN> ::= " then "
<ELSE> ::= " else "
<FIXED> ::= " fixed "
<FLOAT> ::= " float "
<VAR> ::= " varying "
<DEF> ::= " defined "
<LOOP> ::= " loop "
<WHILE> ::= " while "
<UNTIL> ::= " until "
<TO> ::= " to "
<BY> ::= " by "
<REPEAT> ::= " repeat "
<POINTER> ::= " pointer "
<compilation_unit> ::= <stmt>+
<stmt> ::= <dcl_stmt> | <def_stmt>  
<dcl_stmt> ::= <DCL> <identifier> <array_specifier>? <reqd_dcl_attribs> <optional_dcl_attribs>* ";"
<arg_stmt> ::= <ARG> <identifier> <array_specifier>? <reqd_dcl_attribs> <optional_dcl_attribs>* ";"
<identifier> ::= [a-z]+ " "
<def_stmt> ::= ( <PROC> | <FUNC> ) <identifier> <arglist>? <reqd_dcl_attribs>? <block>
<arglist> ::= "(" <identifier> ( "," <identifier>)* ")"
<array_specifier> ::= "(" <integers> ( "," <integers>)* ")"
<integers> ::= [0-9]+  
<reqd_dcl_attribs> ::= <numeric> | (<string> <VAR>?) | <POINTER>
<optional_dcl_attribs> ::= <STATIC> | <based> | <defined>
<defined> ::= (<DEF> ("(" <identifier> ")") )
<based> ::= (<BASED> ("(" <identifier> ")")? )
<numeric> ::= (<base> <scale>?) | (<scale> <base>?)
<binary> ::= <BIN> (<FIXED> | <FLOAT>)?
<decimal> ::= <DEC> (<FIXED> | <FLOAT>)?
<base> ::= <BIN> | <DEC>
<scale> ::= <FIXED> | <FLOAT>
<string> ::= <STRING> "(" <integers> ")"
<block> ::= "{" <arg_stmt>* <dcl_stmt>* <exe_stmt>* "}"
<exe_stmt> ::= (<assignment> | <keyword_stmt>) ";"
<assignment> ::= <identifier> " = " <identifier> 
<keyword_stmt> ::= <call_stmt> | <goto_stmt> | <return_stmt> | <if_stmt> | <loop_stmt>

/* executable statements */
<call_stmt> ::= <CALL> <identifier> <arglist>?
<goto_stmt> ::= <GOTO> <identifier> ( "(" (<integers> | <identifier>) ")" )?
<return_stmt> ::= <RETURN> | (<RETURN> "(" <expression> ")")
<if_stmt> ::= <IF> <expression> <THEN> (<block> | <exe_stmt>) (<ELSE> (<block> | <exe_stmt>) )?
<loop_stmt> ::= <LOOP> (<iterate>? | <repeat>?) ((<while>? <until>?) | (<until>? <while>?))? <block> 
<while> ::= <WHILE> "(" <expression> ")"
<until> ::= <UNTIL> "(" <expression> ")" 
<iterate> ::= <identifier> "=" <expression> <TO> <expression> (<BY> <expression>)?
<repeat> ::= <identifier> "=" <expression> <REPEAT> "(" <expression> ")"

/* expressions */
<expression> ::= <identifier> | <integers>

Expressions are not defined yet (other than being a simple identifier or numeric literal) but you can see the idea here.

I find the tool extremely helpful as I incrementally extend the grammar gradually but the whitespace thing is slowing things down a bit.

Is there a way to cater for this purely using EBNF? Here's a typical test input that I'd expect to parse cleanly:

dcl name(10) string(32);

proc main (arg1) 
{
   arg arg1 string(32);

   loop I = 1 to 100 by 5 until (fail)
   {
     call testutil(I);
   }

}

Of course it won't because the presence of CR and LF etc mess everything up. Also if we could get the tool to tolerate these white spaces then could the test input area be changed so that it is also an expandable text input box, like the BNF editor window itself?

Finally it would be neat too if we could somehow "download" the grammar text (rather than just saving the URL as you support but I find a little confusing). Currently I'm copying/pasting this as I work, into a file on my desktop PC.

I have developed a full PL/I compiler for Windows in the past, like some 20 years ago so I'm very much at home with this but have never used any kind of grammar tool and it is a huge help when exploring options for a new grammar.

Thanks!

How to specify an optional syntax ?

I’m trying to create the following token, expressed as ABNF syntax:

number            = ["-"] 1*digit

The best I could come up with in the BNF Playground is this:

<number> ::= <digit>+ | "-" <digit>+

How would it be possible to express the "-" minus sign as being optional (i.e appearing exactly zero, or one time) ?

Percent sign in grammar breaks "Save BNF as URL"

Enter the following in the Editor tab's grammar input box

<Percent> ::= "%"

hit Save BNF as URL and I get the URL

https://bnfplayground.pauliankline.com/?bnf=%3CPercent%3E%20%3A%3A%3D%20%22%25%22&name=

Opening that in the browser (recent Chrome) and looking at the JS console I see

URIError: URI malformed
    at decodeURIComponent (<anonymous>)
    at f.value (f80ab1d.js:1)
    at f.value (f80ab1d.js:1)
    at Qt (c4c8d66.js:2)
    at cn (c4c8d66.js:2)
    at Object.insert (c4c8d66.js:2)
    at j (c4c8d66.js:2)
    at jn.__patch__ (c4c8d66.js:2)
    at jn.t._update (c4c8d66.js:2)
    at jn.r (c4c8d66.js:2)

but this problem does not manifest for

<Dot> ::= "."

Multiline comments don't work

Problem

Multiline comments appear to not work correctly. Example:

/*
This is a multiline comment.

*/
<gpa> ::= "4.0" | <leading> "." <trailing>
<leading> ::= [0-3]
<trailing> ::= [0-9]

Output:

Uhoh, looks like you have an error: Error: Syntax error at line 2 col 0:

1 /*
2 This is a multiline comment.
 ^

Unexpected "\n". Instead, I was expecting to see one of the following:

A character matching /./ based on:
    comment$ebnf$1 →  ● /./ comment$ebnf$1
    comment → comment$string$1 ● comment$ebnf$1 comment$string$2
    rule →  ● comment
    bnf →  ● rule
A "*" based on:
    comment$string$2 →  ● "*" "/"
    comment → comment$string$1 comment$ebnf$1 ● comment$string$2
    rule →  ● comment
    bnf →  ● rule

Solution (maybe)

Presumably somewhere an incorrect assumption is made about whether some regex matches newlines. Here are a couple of possibilities.

It might be a case of the classic gotcha for the behavior of the . regex operator. The docs for JavaScript regexes say:

Note that the m multiline flag doesn't change the dot behavior. So to match a pattern across multiple lines, the character class [^] can be used — it will match any character including newlines.

The s "dotAll" flag allows the dot to also match line terminators.

Alternatively, often a regex for multiline comments has a subexpression similar to [^*] | \\[*] | [*][^/] | [*]$ | … somewhere. If you don't want to think too hard about it, just throw in another alternative matching a newline: [\n\r\f] | [^*] | \\[*] | [*][^/] | [*]$ | …

Improvement: move Generate Button above output

Problem:
The generate button is under the output, moving the button up and down every time i press it. This usually happens if my BNF contains a "\n"
I would like to be able to spam the button because the code can be so large some outcomes are extremely unlikely, but i have to consciously aim at the button every time I press it.

Solution:
one option could be to simply put it above the output? or to put a scrollbar and a fixed height to make the button fixed?
Thanks a ton, very useful tool!

License?

I am unsure what license this code has. I am asking because I may create a repo with some BNFs of interest to me that work on the web-site and would like to include the grammar help, the markdown found in the file grammarhelp.vue in the repo's readme. The BNFs and EBNFs accepted by your code varies a little from various documents I have read on BNFs. Your grammar helps clarify some of that. A license file would clarify whether I would be allowed to use that text. Naturally, you saying yes or no to using in response to this issue would be just as good.

Thanks for the work on this project, this is a great app and much-needed online.

Playground does not seem to report ambiguous grammars

I’m trying to use the BNF Playground to model my grammar and communicate with others as this is a very handy tool.

The grammar for the language I’m helping design improvements for is originally written using ABNF.

Here is a gist that contains the same grammar in EBNF syntax for use in the playground.

I’m trying to design a new feature and try to change the <sub_expression> rule to accept a more general <expression> on its right-hand side. Thus changing this rule:

<sub_expression> ::= <expression> "." ( <identifier> | <multi_select_list> | <multi_select_hash> | <function_expression> | <hash_wildcard_expression> )

to this:

<sub_expression> ::= <expression> "." <expression>

When doing so within the playground, everything is perfect.
However, when later trying to do the same using my ABNF grammar, I get a lot of reduce/reduce conflicts that signal that the resulting grammar is ambiguous.

Is there a way to detect ambiguous grammars with BNF Playground ?
Would there be a way to specify precedence of some sample constructs ?

Support for epsilon?

Hi, thanks for your great work! It helps me a lot.

I have some questions when using this editor. I don't know how can I use epsilon, i.e. the empty sequence. I've tried "null", "nil", "espilon", but they all don't compile.

lacking symbol for `empty`

I was trying to write a recursive BNF grammar with empty as one of the base cases

<digits> ::= <digit> | <digit> <digits> | ε

however the parser does not recognize ε or ""
would be nice if this is supported

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.