Wednesday, January 15, 2014

Scala/Akka library for serial communication

I like Scala and Akka a lot and am still doing some projects using an Arduino. Akka has a nice new interface for actor based interfacing (see Akka I/O) so I decided to write a little library that bridges the good old RXTX serial port library to it.

It was a rather easy exercise, it only took around 220 lines of code most of which are message definitions. RXTX is still nasty (esp. with regarding the handling of the native libraries), but at least my actor hides to ugly parts.
See my the rxtx-akka-io project on my github profile for the source code and some examples.

Short usage example (inside an akka actor):
override def preStart = IO(Serial) ! Open(port, 9600) 
override def receive = {
  case Opened(operator, _) =>
    println("Connected to port")
    context become open(operator)
}
The operator actor then accepts messages like Write(ByteString) and Close and starts sending Received(ByteArray) messages to the actor that started it.
Failure handling is easy, if something happens the operator actor will crash and leave it to it's parent (the actor that executes the code printed above) to restart it or handle it otherwise.

Happy Hacking!

Thursday, May 27, 2010

gnu.io.PortInUseException

I spent some time today trying to figure out why I kept getting gnu.io.PortInUseException while opening a port. After closing more or less every program that could possibly infere with a usb/serial port I figured out that the exception was just badly named.

On Mac OS X one needs to create the directory (i used 777 rights on it)
   /var/lock
in order to be able to use RXTX at all. Else you just keep getting the damn gnu.io.PortInUseException.

I'm sure this is documented somewhere and I just didn't find it... but many thank to JGrass for the tip.

Wednesday, May 26, 2010

Setup Arduino with Eclipse

While I think the Arduino IDE is great to play around with an AVR microcontroller it reaches its limits when used with bigger projects. They often need a better source code organisation, esp. if one's using C++ classes. Because of that I mostly switch to an Eclipse based development environment after an initial kickoff phase.

The setup of the eclipse based development environment for Arduino is a bit of a challenge. Following my setup procedure, based upon Robert Carlsen's Blog on a Mac OS X Snow Leopard and a Boardiuno:
  • install XCode if not already done (else make will fail)
  • install Cross Pack for AVR development
  • install Arduino IDE
  • Download and install Eclipse for C/C++ developers
  • Install the AVR-Eclipse Plugin to Eclipse
    • Help -> Install new software
    • http://www.eclipse.org/downloads/ is the update site
    • restart eclipse
  • check the paths in Eclipse preferences / AVR / Paths
    • should point to the cross pack
    • Atmel Part Description Files is not needed
  • add a AVRDude config (Eclipse preferences / AVR / AVRDude -> Add)
    • Name: Boarduino
    • Programmer Hardware: STK500 Version 1.x
    • Baudrate: 57600
    • Set port (find the port by 'ls /dev/cu.*', i.e. /dev/cu.usbserial-FTELSJ9T)
  • create a new CPP project (or checkout my template)
    • New C++ Project
    • AVR Cross Target Application
    • don't press finish, but next
    • select hardware (ATMega 328P and 16 Mhz (16000000) for Boarduino)
    • finish
  • Open the properties of the newly created project
    • AVR / AVRDude: Select the programmer ("Boarduino")
    • under C/C++ Build/Settings (for both targets, Debug and Release)
      • under "Additional Tools in Toolchain" check only:
        • Generate HEX file for flash
        • Print Size
        • AVRDude (optional, directly uploads after compilation)
      • under AVR compiler
        • change command from "avr-gcc" to "avr-g++"
        • Directories: add "/Applications/Arduino.app/Contents/Resources/Java/hardware/arduino/cores/arduino"
        • Debugging: no debugging info
        • Optimization: size (-Os)
      • under AVR C++ compiler
        • change command from "avr-gcc" to "avr-g++"
        • Directories: add "/Applications/Arduino.app/Contents/Resources/Java/hardware/arduino/cores/arduino"
        • Debugging: no debugging info
        • Optimization: size (-Os)
      • under AVR C++ Linker
        • Add Library
          • Name: core
        • Add Library Path
          • Path: ${workspace_loc:/Blink/lib}   (if the project name is "Blink")
  • Open Arduino IDE and an example project
    • set your Arduino (in Tools/Board)
    • Click Verify/Compile in the toolbar while pressing shift
    • Extract the folder name from the log-panel (beginning with /var/folders/....)
    • copy the core.a from the folder into <eclipse-project>/lib/libcore.a
  • Compile the project in Eclipse


Notes:
you might have to define 
    extern "C" void __cxa_pure_virtual(void);
    void __cxa_pure_virtual(void) {}
in your projects main.
And also:
    #undef int
    #undef abs
    #undef double
    #undef float
    #undef round
if you get compile errors in math.h and several other system-files.


Versions used:
  • Eclipse 20100218-1602 (3.5 SR2)
  • AVR Eclipse 3.2.1
  • Arduino IDE 0018
  • CrossPack AVR 20100115

Good luck.

Thursday, May 6, 2010

Read/Write binary data with Scala

In my project to communicate between my notebook and an Arduino over XBees I need to send binary commands to the XBee. The protocol is defined approx. like this: every packet start with 0x7E and then two bytes containing the length of the packed then the payload and afterwards a checksum.
So I decided to write a little library that allows me to parse and compose these commands in a natural way. The parsing should use pattern matching.

To define a structure use something like this:

val myPattern = <<(byte, integer, integer, byte)>>

('<<' is a imported function, the '>>' is just decoration, that returns itself)

then you can use

val bytes: Seq[Byte] = myPattern(12, 33321, 24432, 0)

to generate a binary representation (i.e 0x12, 0x00, 0x00,  0x82, 0x29, ...). To a byte sequence use

bytes match {
case myPattern((a,b,c,d), rest) =>
a should be(12)
b should be(33321)
c should be(24432)
d should be(0)
rest should be(Nil)
}

The variable "Rest" in the example will contain everything in the Seq[Byte] after the matched sequence.


It also allows to check for fixed values (in the example above 0x7E in the first byte):

val myPattern2 = <<(fix_byte(0x7E), integer, integer, byte) drop1
myPattern2(1234, 4321, 12) //will be 0x7E, 0x00, 0x00, 0x04, 0xD2


And you can map a pattern to some class:

case class Color(red: Byte, green: Byte, blue: Byte)

val rgbPattern = <<(byte, byte, byte)>>>(
(c: Color) => (color.red, color.green, color.blue),
t => Some(Color(t._1, t._2, t._3))
)

But what makes it really powerful is the ability to nest those patterns

val colorfulPattern = <<(fix_byte(0x7E), rgbPattern, rgbPattern, integer) drop1
val data = (0x7E :: 33 :: 21 :: 11 :: 0 :: 100 :: 12 :: 0 :: 0 :: 0 :: 4 :: Nil).map(_.toByte)
data match {
case colorfulPattern((foregroundColor, backgroundColor, pixelsToFill), _) =>
foregroundColor should be(Color(33,21,11))
backgroundColor should be(Color(0, 100, 12))
pixelsToFill should be(4)
}

so it's pretty easy to define complex structures pretty fast, easy and reusable. The framework also provides possibilities to parse/serialize lists (even of "complex" objects) and optional values.


Just check out the code a GitHub and feel free to use it and contribute to it!

Now on Github

As many other Scala-project are already present on GitHub I decided to host my little projects there as well. Check out my GitHub Profile. Currently there are only two projects:
  • scala-base: My base classes, i. e. Durations, BinaryParsing, Actor-library and Erlang OTP-like stateserver and supervisor
  • scala-xbee: An library to communicate with a usb-port attached XBee (and obviously XBees attached to this one).
I'll blog more about the projects later.

Monday, May 3, 2010

Run sbt inside emacs

Today I found a nice emacs addon that allows you to run sbt inside emacs. It even has clickable compiler errors (although I don't need those because ensime does this nicer).
Actually it's mentioned in the scala wiki, but I managed to over read it until now :)

Add (setq comint-scroll-to-bottom-on-output t) to autoscroll to the bottom when new output is written (M-x eval-expression).

Sunday, May 2, 2010

Emacs and sbt

After selecting sbt as my new build-environment I still needed an editor to code in. First I went with TextMate with a Scala Bundle (don't remember which one, I installed that some time ago). While it offers just code highlighting and some code templates it works just fine. I didn't miss code completion all that much (probably because it didn't work very well in Eclipse either). But what I really missed was  compilation-error highlighting. I spent some time coding with the sbt-iTerm window beside the TextMate-editor and using Command+L (enter line number) to jump to the errors that showed up in iTerm. Works, but nothing to write home about..

I remembered a nice video about Aemon Cannon showing his ensime-Emacs mode (video on youtube). He shows syntax highlighting (actually that's provided by the scala-mode), code completion, compilation errors, type inspection and package overviews. Quite impressing, isn't it? And what I liked best about it, is that it directly uses scala itself (running in a "server-process") to provide those features. So they're accurate and not "guessed" by a second parser implementation. Also all the stuff happens in the background, so it doesn't slow down your typing. Great stuff!

So here's how I installed it

  • Install/Update to Emacs 23 for Mac OS X according to this blog. Ensime needs the Emacs 23.
  • Spent some time with various Emacs tutorials to refresh my Emacs-skills :)
  • Install the scala-mode for emacs as described on scala-lang.org
  • Download Ensime and unpack it to some path (i.e. to ~/scala/emacs/ensime)
  • Make sure you got a 'java' and a 'scala' on the path (i.e. ln -s /Applications/scala/bin/scala /usr/local/bin/scala)
  • add some lines to .emacs as described in the Ensime readme
  • create a .ensime file in your project root. Mine looks as follows (current version):
(
  :server-root "/Users/ms/scala/emacs/ensime/"
  :server-cmd  "bin/server.sh"
  :server-host "localhost"
  :server-env ()

  :project-package "ch.inventsoft.scalabase"
  :source ("src/main/scala")
  :exclude-source ()
  :classpath ("lib/jsr166y.jar"
        "lib_managed/scala_2.8.0-SNAPSHOT/compile/logback-classic-0.9.20.jar"
        "lib_managed/scala_2.8.0-SNAPSHOT/compile/logback-core-0.9.20.jar"
        "lib_managed/scala_2.8.0-SNAPSHOT/compile/slf4j-api-1.5.11.jar"
        "lib_managed/scala_2.8.0-SNAPSHOT/plugin/continuations-2.8.0-SNAPSHOT.jar"
        "project/boot/scala-2.8.0-SNAPSHOT/lib/scala-compiler.jar"
        "project/boot/scala-2.8.0-SNAPSHOT/lib/scala-library.jar"
        "lib_managed/scala_2.8.0-SNAPSHOT/test/scalatest-1.0.1-for-scala-2.8.0.RC1-SNAPSHOT.jar")        
)
  • fire up emacs, open a scala file of your project. If it doesn't have syntax highlighting enter 'M-x scala-mode'
  • Enter 'M-x ensime' and answer the questions.
  • See the Ensime readme for all the available shortcuts (Tab, C-c t, C-c p)
  • Feel happy :)

I still got some problems with the inspector (didn't figure out how to have it open in a separate window, probably due to my incomplete emacs know-how), but overall it works just great. With sbt ~test-quick executing all tests as I change the code it provides very fast feedback.

And it'll get even better. I just read on the scala-Maillist, that Cannon's proposal for Google's summer of code has been accepted. Looking forward to that! Great job, Aemon