Saturday, July 26, 2014

ASTROGUN!



ASTROGUN is an Asteroid shooting game I developed along with Maayan Dreamer for the Jerusalem Mini Maker Faire (the link is in Hebrew), held in June 2014.
 The game is pretty simple - the player stands and has to shoot Asteroids that are coming towards him from any direction, before they hit him. A RADAR-like view helps the player locate the Asteroids around him.
The most interesting thing is the display system.  We build a HUD - heads up display - which is a display that shows an image overlaid on the background.

Check out how it looks like in the video below:


How it Works

In the heart of the Astrogun lies a Raspberry Pi computer. An IMU card connected to it (Sparkfun's MPU-9150 breakout board) providing it with the ability to sense the orientation the unit's orientation. Having this information, the Pi is able to draw the various elements (Asteroids, bullets, explosions), as seen from that specific angle. When the player moves, the graphics move ayour'ccordingly, giving the "object in the room" sense.

The display system comprises of two main elements: an LCD panel and a beamsplitter glass (also known as Teleprompter glass). This glass has a unique feature - it is both transmissive (like a window) and reflective (like a mirror). The player, looking through the glass sees both the image behind the glass and the image projected from the LCD.
Anyone who is familiar with basic optics will immediately notice that I'm a little bit cheating here. The system lacks one important component - a collimation lens. In real HUD systems, this lens projects the imager image to infinity, creating an illusion that the graphics is in fact "on" the object the user is looking at. In our case, the short development time hindered us from complex optical structures. Nevertheless, the experience of object-in-the-room is still there, to some degree.



As for the software, the game is not very computationally demanding (set aside the graphics rendering process, which is handled by the GPU). The development time, on the other hand, was definitely demanding. Therefore, Python was a natural choice. I used the excellent Pi3D library to create the graphics, while the rest of the game logic is written in pure Python. In order to determine the orientation, I used the RTIMULib library, which reads the sensors and fusions its data into orientation angles (I also contributed a Python binding module for that library, which was written for this project). Sound effects are played using the PyGame library.

Finally, the mechanics. Most of the electronics (RPi, IMU, power supplies and a few more) were fitted nicely within the body of a toy gun, which was sourced from a local toy store. The display system, which comprises the LCD, its controller and the beamsplitter glass are held in position by a glass epoxy structure which positions them in the location and angle required (the glass and the LCD must be positioned in a 45 degree angle, otherwise the image will be distorted). The Raspberry Pi is connected to the controller using an HDMI cable. The trigger of the gun had an electric contact for its original purpose (flashing LEDs and making noise), and it was re-routed to one of the GPIO pins.


Source Code

All the source code of the project is available through GitHub. Unfortunately, the mechanical structure is ad-hoc and not documented.


Thursday, March 6, 2014

Arduino library for TM1637 Display Module

I needed a small numerical display for a project I'm working on. I found this one on Dealextream. It looks great - a 4 digit module, with a driver and a serial interface - perfect match for my requirements. The product page mentioned that it is driven by a chip called TM1637. A quick search at Google lead me to an Arduino library, made by SeeedStudio that is capable of communicating with the module.

Three weeks later, I have the module at hand. I'm connecting it to an Arduino board, installing the library and uploading one of the example files. Nothing. Total blackness. On the hardware side, with only two digital pins, it's pretty hard to mess things up, so the suspicion falls on the software. The next step is trying to get the datasheet of the TM1637. The chip is made by a company called Titan Microelectronics, which holds a product page for it. Sadly, the link to the datasheet is broken. Searching again, filtering all the "datasheet.com" etc., I find this datasheet, in plain Chinese. With the help of Google Translate, and SeeedStudio's library, the communication protocol gets revealed. The chip uses the I2C protocol, and the sequence required to write display data is as follows (ST - start condition; SP - stop condition):

  • ST - COMM1 (0x40) - SP
  • ST - COMM2 (0xC0) + the first digit to be written
  • digit1 - digit2 - ... - digit4 - SP
  • ST - COMM3 (0x80) + the display brightness - SP

Having all that at hand, I wrote a new library, implementing this protocol. The library is available at GITHUB, including a sample sketch demonstrating its capabilities. The repository also includes a README file explaining how the library should be used and how the module should be connected to the Arduino.

Why did SeeedStudio's library fail?

Browsing through SeeedStudio's code, I found two problems that might cause it to malfunction.
The first one is this:

  digitalWrite(Clkpin,LOW); //wait for the ACK  
  digitalWrite(Datapin,HIGH);  
  digitalWrite(Clkpin,HIGH);   

The digital output pins are bit-banged to create the I2C signal, but there's no delay. This gives a toggling rate much beyond the specified 400KHz. It's possible that Seeed were testing their module with an 8MHz Arduino, while my module was 16MHz, raising the toggle rate even further away from the specification.

The second problem also arises from the code snippet above. I2C is wired-and bus, meaning it should never be driven high.When a logic '1' is desirable, the output of the Arduino should be put in high-impedance state allowing the pull-up resistor to pull the line to its high level. This is unlikely to cause an immediate problem, but in the long term it may cause the reliability of the components to degrade.

Monday, January 6, 2014

Using an Android phone as a secure OpenVPN Gateway


I'm running a small OpenVPN setup at home, through which I can connect to my home network from various places securely and safely. I really like OpenVPN. It's robust, safe and fairly easy to set up. There is only one small caveat - it is not a standard VPN client in Windows. In order to use it, an OpenVPN client is required. Such client exists, of course, and it's can be downloaded and installed on any computer. There are occasions, though, that downloading and installing software is either impossible or inappropriate. For example, using a company provided notebook computer or a friend's computer.
One way to overcome this limitation is to use of an Android smartphone as a VPN gateway. The phone runs OpenVPN and has access to the private network. The client computer is tethered to the phone and set up in such way that access to the private network addresses from the PC is routed through the phone and forwarded over the secure tunnel. This is the ideal solution - the computer doesn't have to know anything about OpenVPN, no software has to be installed and no key has to be deployed. The only tweak required - sometimes - on the PC side is adding an entry to the routing table. In Windows 7 it seems that it can even be done without administrative privileges.
In order for this setup to work, some tweak are required on the phone side. The remaining of this post explains more about it.

Prerequisites

First of all - a rooted Android phone. Mine is a Samsung Galaxy S-II (also known as GT-I9100) with CyanogenMod ROM. I've never tested this procedure on any other phone, but I'm sure it will work on most of them.
The second requirement is a working OpenVPN setup. I won't get into the details of this setup, there are plenty of tutorials on the Internet. When OpenVPN works computer-to-computer, it's very easy to migrate it to the phone - just install the OpenVPN client from Google Play, put the configuration files on an SD card and let OpenVPN on the phone know where the files are.

Procedure

We will use the iptables utility to instruct the phone to forward IP traffic through the secure tunnel. For the sake of the discussion, let me assume that the private network is on the 192.168.2.0/24 subnet.

The first step is instructing the phone to forward packets to/from the secure tunnel (tun0) and Masquerade them:

iptables -I FORWARD -i tun0 -j ACCEPT
iptables -I FORWARD -o tun0 -j ACCEPT
iptables -t nat -A POSTROUTING -o tun0 -j MASQUERADE     

These commands can be entered directly using a phone terminal software (such as the one installed by default when installing CyanogenMod on the phone), or better using an SSH server such as this one.

The second step is to enable packet forwarding from the interface tethered to the PC. There are multiple options here, and it may be necessary to detect which of the network interfaces is use for which purpose. This can easily be done with the netcfg command on the phone. Run it once, without the tethering and the once again with the tethering activated. The network interface that was used for this purpose should go from DOWN to UP state, and an address should appear. In my phone, the interfaces are wlan0, rndis0 and bt_pan for WLAN, USB and Bluetooth tethering respectively.
And now back to the iptables command:

iptables -I FORWARD -o rndis0 -j ACCEPT 
iptables -I FORWARD -i rndis0 -j ACCEPT

(replacing rndis0 with the appropriate interface name).

Finally, we have to tweak the routing table on the PC to redirect the traffic of the private network to the right place. This step is not always required - if the PC's only network connection is the phone, this will happen naturally.
For all other cases, a new route is required. The routing table on Windows is managed using the route utility. First, open a command line window. In Windows 8, it must be run as an administrator. Now, we'll have to identify the network interface used for the tethering:
 
route print

This command prints the routing table, but in this stage we're only interested in the header of the result, the one listing the network interfaces on the computer:





In the case of Bluetooth tethering the first interface in the example is the one being used. In the case of WLAN tethering we'll select the wireless LAN adapter (not shown) and in the case of USB tethering it is shown as USB to Ethernet adapter. The first number in each line is the interface number.
Now, the route is created as follows:

route add /p 192.168.2.0 mask 255.255.255.0 route 192.168.44.1 if 23

This address 192.168.2.0 is the address of the private network; the address 192.168.44.1 is the phone's address (on the tethering interface, obtained with ipconfig) and the number 23 is the network interface number as demonstrated above. The /p switch makes the route permanent, meaning that we won't have to touch the routing table every time the phone is connected.

That's it! Now, you should be able to access the private network from the PC.

Just one additional note: to make the changes permanent on the phone side (that is, they will be available after the phone is being reset), create a file called userinit.sh in /data/local and put all the iptable commands  in it. For example:


#!/system/bin/sh

# Add iptables rules for forwarding packets from tethered interface
# to OpenVPN connection
iptables -I FORWARD -i tun0 -j ACCEPT
iptables -I FORWARD -o tun0 -j ACCEPT
iptables -t nat -A POSTROUTING -o tun0 -j MASQUERADE

# For USB
iptables -I FORWARD -o rndis0 -j ACCEPT
iptables -I FORWARD -i rndis0 -j ACCEPT

# For Bluetooth
iptables -I FORWARD -o bt-pan -j ACCEPT
iptables -I FORWARD -i bt-pan -j ACCEPT

# For WLAN
iptables -I FORWARD -o wlan0 -j ACCEPT
iptables -I FORWARD -i wlan0 -j ACCEPT

Wednesday, June 5, 2013

xser - First Assembled Board

The first xser board is now assembled and working. I've made some progress with the software, mostly migrating the prototype software to the new board (a different processor and I/O mappings). It has now basic functionality, transmitting and receiving serial data. The LCD is also working, and with the demo software written for the prototype it shows the COM port number to which the adapter is attached.
The software is accessible through the GitHub repository.

Front Side
Back Side


Thursday, May 2, 2013

Is BeagleBone Black a potential gamechanger?

Last week a new board joined the ever-growing family of low cost ARM boards - the BeagleBone Black. Like the original BeagleBone, it's powered by a TI AM3899 and has a similar form factor and expansion connectors, so it can be used with all the expansion boards ("capes") available for the its predecessor. There are several differences between the old BeagleBone and the new one, but the most important one is the price. With a 45$ tag price it's only 10$ more than a Raspbery Pi (Model B). Taking into account the fact that it has built in Flash memory makes this gap even smaller, since no SD card is required anymore.

At first sight, it looks like a Pi killer. But the Black, like its old brother, the original BeagleBone, falls short in one important area - video. It doesn't offer any decoding (not to mention encoding) acceleration leaving it to the processor core. Additionally, the built in HDMI interface can't handle 1080p video at all. These facts leave the Black out of media player game and send us back to the good old Pi.

Nevertheless, I think that the new board is great a opportunity. With built in storage and direct LCD panel interface it is a great for standalone GUI applications, as well as applications that require more processing power provided by the Raspberry Pi.

Wednesday, April 10, 2013

xser parts and smart-prototyping.com impressions

xser parts are here!

A few days ago, I've received the package with all the components. Everything (PCB and components) was ordered from a company called NOA Labs, which operates the smart-prototyping.com Web site.I first read about this site in a Dangerous Prototypes blog post. They offer a wide range of services - PCB manufacturing, component sourcing, mechanical manufacturing, test equipment and much more. Let me try to summarize my experience with them.

Pre-Order and Order

The company is run by German guy named Alex who lives in China. This is a big advantage, since you can actually communicate with him in plain English. I got very quick responses to all my queries, sometimes instantly. They've been able to get all the components I needed, including the (relatively new) PIC18F24K50, which is absent from most distributors' inventory.
The PCB quotation is quite simple and can be easily calculated using the Web site. Component quotation is trickier. They have no cataloging system like Digikey, Mouser etc., so the component definition must be full and precise. Usually it took them a day or less to return the quotation (it's a small BOM - about 15 parts).
It worth noting their willingness to accept such a small quantity order. Until now, the only way to get a variety of components in small quantity was through the big distributors - which means a lot of money (especially the shipment costs to Israel, which are very high). This is a great new option, I hope it's profitable enough for them to keep it running.

The PCB

The PCB service is quite conventional, with a minimum of 6 mil track width and track-to-track spacing. The xser PCB design is simple and does not stress these limits in any way. The order is for 10 units, I actually got 12, which is very nice and leaves some headroom for soldering tests and oven calibration.
Visually, the PCB looks very good. It is supposed to be 100% tested (in the order page on their Web site, there is an option to choose between 90% and 100% testing without additional cost ... Hmm, tough decision). There is no certificate, report or other evidence that this test has been actually made, so I'll have to trust them on this one.
Overall, being one of the cheapest options around, I couldn't be happier.


Components

I got all the components I ordered - no missing parts, no spares. The packaging, however, had some quirks.

 
 Most of the components came as cut taps, in anti-static bags. This is how things should be.



D-Type connectors came in a plastic bag, without any protection on the pins. There are some minor distortions, but nothing that can't be fixed.


I ordered two PIC12F615s in SOIC package (for a different project). As seen in the picture, their just thrown in an bag. At least it's an anti-static one. This is a no-no.




LCD glasses are very sensitive to static charges. They were placed on an anti-static foam, but there was another piece of regular Styrofoam placed on the top. It should have been anti-static as well.


Some component bags bear Chinese markings. While it's not a problem to understand what is the component in the bag, there is no way to tell who is the manufacturer of the component and what is the original part number.

Overall

My overall impression was very positive. I'll definitely continue to work with them on my next projects.


Next stop - assembled circuit.

Saturday, March 9, 2013

xser - Schematic and Layout

xser is progressing towards initial production.
The circuit schematic and the PCB design are ready and available through the project's github repository.
Beside the (obvious) LCD, I've included some neat features in the unit:
  • Full support for RTS/CTS lines - this is important for those who are using the Arduino bootloader.
  • Dual drive - The unit supports both RS-232 signaling levels and flexible logic levels - from 5V down to 1.6V. This range covers all the development boards I'm familiar with directly, without additional level shifters or special purpose adapters. The xser unit will switch to the logic level signaling as soon as the target VCC is connected.
  • Pushbutton - will be later used to implement functions such as auto baud detection and direct information retrieval (baud rate, drive type, etc.)





PCB Front Side
PCB Back Side
The circuit is based on the PIC18F24K50. This is a new chip from Microchip, a successor to their successful 18F245x family. This chip brings some useful features - it can run directly on 5V from the USB, it is cheaper that the older family and finally, it has a circuit that can derive accurate clock from the USB, making it possible to work without external crystal even in full speed USB. At least so they say.
The processor drives the LCD directly (taking most of its I/O pins) and its UART pins are connected to both drivers - a MAX3222 for RS-232 level signaling and a pair of TI SN74LVC2T45 level shifters that can accept any signaling level from 1.6V up to 5V.
The circuit can use only one of the driving method at any given time. When an external target voltage is applied to the power pin in J2, the RS-232 driver is shut down allowing the level shifter to drive the signal into the controller. When no power is connected to that pin, the MAX3222 operates normally and receives signal in RS-232 levels.

The PCB measures approximately 50x35mm, enabling it to be produced in some cheap manufacturing services that restrict the size to 50x50mm.