Skip to content

Latest commit

 

History

History
167 lines (115 loc) · 4.66 KB

CONTRIBTUE.md

File metadata and controls

167 lines (115 loc) · 4.66 KB

For Contributors

Means of contribution

You can help with this project by

  1. Fixing bugs (see issues for bugs)
  2. Implementing a library (please post it as an issue first so others know you are working on it)
  3. Adding/fixing test cases
  4. Introducing new features
  5. Discussing and sharing your thoughts (in issues)

Getting started

If you want to leave your footprints in this project, you can

  1. Fork it
  2. git clone then npm install
  3. Leave dist and lib alone, because they are automatically maintained
  4. (optional) grunt # default task of grunt is to build and watch
  5. Make your contribution
  6. grunt build
  7. grunt test
  8. Commit, push then send a pull request here.

Use grunt build to update files in dist and lib folders.

Use grunt test to make sure that you did not break anything.

The syntax parser is generated by PEG.js. Put your .pegjs file in pegjs/ folder, then use grunt peg:build to generate your syntax parser (or just use grunt build). The parsers will be created in lib/ folder under the same name.

The project is written in CoffeeScript. And you are encouraged to use it as well. It has a python-like syntax that utilizes forced indents to "free" people from brackets and semicolons. I think CoffeeScript code is generally more readable.

Any PR is welcome.

Using node-inspector

We need to enable harmony flag to run node-debug. For example, use the following command to debug JSCPP with test/8.bit.cpp as input.

node-debug --nodejs --harmony demo/debug 8bit

Remarks

This part contains detailed remarks on this project.

On fixing bugs

If you find the bug, please post it to issues first before trying to fix. Because it may just be a misuse.

There are 4 phases during an interpretation. Namely, preprocessing syntax parsing, preprocessing handling, syntax parsing, interpretation. And they handled by different modules.

If the bug was not covered by existing test cases, you are highly encouraged to add the test cases for it. See "On adding/fixing test cases" subsection for details.

On implementing a library

All libraries are located in src\includes folder. Each library should export an object with load method. You can also use rt.load("dependency") to load other libraries. Every library will only be loaded once.

Don't forget to add your library into launcher.js.

On adding/fixing test cases

Each test can have many source files and many input cases. First you need to put your C++ source file in test\ folder. Then you add the test description in test\test.json. Each test description reads like this:

"A+B": {
    "after": ["cincout"],
    "cpp": ["A+B.cpp"],
    "cases": [{
        "in": "10 506",
        "out": "516"
    }, {
        "in": "-24 -123",
        "out": "-147"
    }]
}

Each test description has a "after" field that requires this test to be run after the designated tests. When all prerequisite tests have passes, the test will start immediately. Each source file in "cpp" field will be tested against each input/output case. Not passing a "in" or "out" field will have the same result as passing an empty string.

Sometime you need to test for exceptions. You can use "exception" field in a test case:

"8bit": {
    "after": ["A+B"],
    "cpp": ["8bit.cpp"],
    "cases": [{
        "exception": "6:3 overflow during post-increment 256\\(unsigned char\\)"
    }]
}

The exception is tested as a regex rather than plain string matching.

On introducing new features

You should open and issue for enhancement first. Other people can probably give some hints.

On discussing and sharing your thoughts

Just open an issue for discussion.

Design details

Here describes some detailed information.

Types

The inner structure of value of each type.

Primitive types

bool

  • t:
    • type: "primitive"
    • name: "bool"
  • v: {1 or 0}

char

  • t:
    • type: "primitive"
    • name: "char"
  • v: {char code}

other

  • t:
    • type: "primitive"
    • name: {type name}
  • v: {type value}

Pointer types

Normal pointer

  • t:
    • type: "pointer"
    • ptrType: "normal"
    • targetType: {type of target}
  • v:
    • target: {target}

Array pointer

  • t:
    • type: "pointer"
    • ptrType: "array"
    • eleType: {type of element}
    • size: {size of array}
  • v:
    • target: [{type-values}]
    • position: {offset}

Function

  • t:
    • type: "pointer"
    • ptrType: "function"
    • retType: {return type}
    • signature: {signature(rt.makeParametersSigniture)}
  • v:
    • target: {f(rt, _this, args...){}}
    • name: {name}
    • defineType: {class type}
    • args: {signature(rt.makeParametersSigniture)}
    • retType: {return type}