All Projects → VedantParanjape → simpPRU

VedantParanjape / simpPRU

Licence: MIT license
Intuitive language for PRU which compiles down to PRU C

Programming Languages

c
50402 projects - #5 most used programming language
Yacc
648 projects
C++
36643 projects - #6 most used programming language
Lex
420 projects
CMake
9771 projects
python
139335 projects - #7 most used programming language
Makefile
30231 projects

Projects that are alternatives of or similar to simpPRU

bison-flex-cpp-example
GNU Bison and GNU Flex C++ example
Stars: ✭ 145 (+168.52%)
Mutual labels:  flex, bison-grammar
epilepsia
Beaglebone cape for driving up to 32x64 Neopixels (WS2812 LEDs).
Stars: ✭ 15 (-72.22%)
Mutual labels:  beaglebone, beagleboard
ipv6-dhclient-script
IPv6 w/ dhclient configuration script (Debian/RedHat-based distros)
Stars: ✭ 68 (+25.93%)
Mutual labels:  debian
DSAC
DockSTARTer App Config helps you configure some of your Docker apps!
Stars: ✭ 20 (-62.96%)
Mutual labels:  debian
polscan
Zero-setup SSH-based scanner with extensive visualizations for Debian server inventory, policy compliance and vulnerabilities
Stars: ✭ 57 (+5.56%)
Mutual labels:  debian
EasySeedbox
Easy Seedbox is an unobtrusive transmission seedbox installation script for Ubuntu and Debian systems
Stars: ✭ 34 (-37.04%)
Mutual labels:  debian
Boostnote-packages
Repo containing .rpm, .deb and Boostnote app folder
Stars: ✭ 31 (-42.59%)
Mutual labels:  debian
tomcat role
Ansible role to install Apache Tomcat Java Servlet Container
Stars: ✭ 13 (-75.93%)
Mutual labels:  debian
dots
Completely automated desktop setup, configuration and maintenance using Ansible
Stars: ✭ 60 (+11.11%)
Mutual labels:  debian
react-styled-flexbox
A Flexbox React component harnessing the power of styled-components
Stars: ✭ 30 (-44.44%)
Mutual labels:  flex
build-raspbian-image
Builds a minimal Raspbian Stretch image
Stars: ✭ 40 (-25.93%)
Mutual labels:  debian
Exagear-For-Termux
Non official modified version of Exagear for Termux and proot based environemnts - Anlinux, AndroNix, UserLand and etc.
Stars: ✭ 98 (+81.48%)
Mutual labels:  debian
pg dba scripts
PostgreSQL DBA scripts
Stars: ✭ 30 (-44.44%)
Mutual labels:  debian
flexui
A light UI for C++ with XML and CSS support
Stars: ✭ 21 (-61.11%)
Mutual labels:  flex
ansible-haproxy
Installs and configures HAProxy
Stars: ✭ 19 (-64.81%)
Mutual labels:  debian
emrah-buster-templates
The templates of the emrah-buster installer.
Stars: ✭ 57 (+5.56%)
Mutual labels:  debian
flex-bison-indentation
An example of how to correctly parse python-like indentation-scoped files using flex (and bison).
Stars: ✭ 32 (-40.74%)
Mutual labels:  flex
ansible-mdadm
No description or website provided.
Stars: ✭ 48 (-11.11%)
Mutual labels:  debian
NETNOOB
A simple program written in bash that contains basic Linux network tools, information gathering tools and scanning tools.
Stars: ✭ 105 (+94.44%)
Mutual labels:  debian
beagleg
G-code interpreter and stepmotor controller for crazy fast coordinated moves of up to 8 steppers. Uses the Programmable Realtime Unit (PRU) of the Beaglebone.
Stars: ✭ 107 (+98.15%)
Mutual labels:  beaglebone

Logo

Intuitive language for PRU which compiles down to PRU C.

Explore the docs »
Report Bug · Tutorials . Request Feature · Send a Pull Request

Table of contents

Brief overview of PRU-ICSS

The PRU is a dual core micro-controller system present on the AM335x SoC which powers the BeagleBone. It is meant to be used for high speed jitter free IO control. Being independent from the linux scheduler and having direct access to the IO pins of the BeagleBone Black, the PRU is ideal for offloading IO intensive tasks.

It is a low-latency micro-controller subsystem, which provides real-time processing capability lacking in Linux. PRUs are part of the PRU-ICSS, “Industrial Communications Subsystem”. They are free from running on an operating system, and thus can be dedicated to a single function.

The PRU cores were created to be non-pipelined, single-cycle execution engines. This means that all instructions (except for memory reads and writes) complete in a single cycle. Since there is no pipeline, the PRU cores are completely deterministic: the PRU cores will not rearrange instructions during execution.

The PRU-ICSS can also read from or write to external pins in a single cycle using a PRU core register (R30/R31). With a PRU core running at 200 MHz, this means that an external signal change can be detected in as little as 5 nanoseconds. This also means that the PRU can toggle external pins with as fast as 5 nanoseconds.

The PRU-ICSS also has an interrupt controller, it does not support asynchronous interrupts as they introduce jitter in execution time and reduce determinism. Instead it supports an efficient polling system.

What was the need for simpPRU ?

Programming the PRU is a uphill task for a beginner, since it involves several steps, writing the firmware for the PRU, writing a loader program. This can be a easy task for a experienced developer, but intimidating for a beginner.

This problem was solved earlier by pruspeaks project, but it inflicts serious restrictions on PRU, as PRU0 runs a bot speaks interpreter and PRU1 takes care of generating PWM signals. Already PRU has meagre resources, so emulating a VM on top of PRU leaves very less room to use PRU for what it is meant, deterministic control and fast read writes.

How does simpPRU simplify things ?

simpPRU simplifies this process to a great extent. Since it has a syntax quite similar to python, it is easier to code in simpPRU. It emits code in C, which is then compiled into binary using pru-gcc. So, it is as good as writing code in PRU C in terms of efficiency and functionality and far less in complexity.

Since, loading the firmware using sysfs class is a challenging and time consuming task, simppru helps in doing that by loading the firmware into /lib/firmware. Since, using sysfs classes to use RPROC and RPMSG is challenging, simppru-console takes care of it, and provides a intuitive and usable GUI to start/stop PRU and read/write to PRU using remoteproc.

Implementation details of simpPRU

simpPRU is a compiler which uses flex to generate lexical analyser, and bison to generate a parser. It uses custom code printer written in C. It emits code in PRU C.

A compiler has 3 main components:

  • Lexical analyser
  • Parser
  • Code printer

Lexical analyser

This is the simplest step. Given our grammar, we need to break down our input into a list of known tokens. As mentioned before, our grammar has tokens, namely, identifiers, numbers (integers and floats), the mathematical operators, parentheses, braces, keywords, etc.

This step basically reads from the input files, and generates tokens according to the regex exp specified in the flex file. The tokens are defined in lexer.l, and the actions that need to be taken after detecting a token is specified in this file itself. For example, if it finds, "int" in the input file, lexer will return a token say KW_INT to the parser.

Parser

This is the most challenging part. We need to parse the list of tokens that we received from lexical analyzer, and evaluate these using language grammar to make sense of the tokens. The language grammar is defined in a bison file named parser.y.

We use a GLR Parser, all tokens are stored in the symbol table, which is a hash table which stores values of the variables, with the variable name as the key, symbol table is defined in symbol_table.c.

After this step, we do semantic parsing whose result is an abstract syntax tree, AST is a tree data structure which stores various token as it nodes, such that it can represent the code in an abstract way in memory. AST is what represents our language in memory, AST related functions are defined in ast.c.

Code printer

The next step in a compiler is to naturally take this AST and turn it into machine code. This means converting each semantic node into the equivalent machine instruction or equivalent C code in this case.

For this step, we traverse the AST in a breadth first depth first approach, and print the equivalent C code in a output file. In this step it also keeps track of the GPO/GPI pins used, and sets them to appropriate mode using config-pin, relevant functions are defined in pin_config.c.

It prints wrapper functions in the generated code, like simple functions to digital read, digital write, send rpmsg, start/stop counter, delay, read counter, etc.

This code printer is defined in code_printer.c

Usage

Please refer to this simppru usage instruction page on readthedocs

Please refer to this simppru-console usage instruction page on readthedocs

Language Reference

Please refer to this language reference page on readthedocs

Examples

For example codes, please check example page on readthedocs

Building from source

Dependencies

Build

git clone https://github.com/VedantParanjape/simpPRU.git
cd simpPRU
mkdir build
cd build
cmake ..
make 

Install

sudo make install

Build debian package

sudo make package

Building using Docker Image

These images have all dependencies installed, just run the commands described in build, inside the docker image and then run sudo make package to generate a debian package.

Installation from debian package

Download

Download the latest debian package from: https://github.com/VedantParanjape/simpPRU/releases/latest
Download amd64 package for x86_64 systems and armhf package for arm32v7 systems

Install

sudo dpkg -i simppru-<version_number>-amd64.deb

replace <version_number> with the appropriate version of the downloaded package

Contributing

Contributions are what make the open source community such an amazing place to be learn, inspire, and create. Any contributions you make are greatly appreciated.

  1. Fork the Project
  2. Create your Feature Branch (git checkout -b feature/AmazingFeature)
  3. Commit your Changes (git commit -m 'Add some AmazingFeature')
  4. Push to the Branch (git push origin feature/AmazingFeature)
  5. Open a Pull Request

License

Distributed under the MIT License. See LICENSE for more information.

Acknowledgements

Known Issues

  • Control statements (break/continue) can be called inside any compound statement, so calling it inside if loop will throw a error while compiling the generated C code.
  • Return statements can only be called at the end of the function, i.e, it must be the last statement in the function declaration, other wise it won't register a return statement and either throw a error or exhibit undefined behaviour.

Notes

When we pass -mmcu=am335x.pru0 to pru-gcc compiler, a macro is defined by the compiler which can be used in the code. Macro is __AM335X_PRU0__. It is set to 1 if pru0 option is passed, and it is undefined if pru1 option is used. It can be used as follows:

#ifdef __AM335X_PRU0__
    #define PRU_NUM 0 
#else
    #define PRU_NUM 1
#endif

Refer: dinuxbg/gnupru#36

Resources

Note that the project description data, including the texts, logos, images, and/or trademarks, for each open source project belongs to its rightful owner. If you wish to add or remove any projects, please contact us at [email protected].