Rada's workshop

Programming

IOT Project

A technology known as "Internet Of Things" is a concept that, among other things, allows the connection and control of home appliances. For this purpose, I made a set of "opensource" projects under the common name "Ujagaga IOT".

It started as a wish to make several LED lamps that I could turn off using one button. Now I have, via a local WiFi network connected LED lamps, a thermostat, a thermometer, an NTP clock that is synchronized over the Internet, a router through which I can access all the devices from that set, a multimedia remote for a computer and an Android application that scans and lists all devices from Ujagaga IOT projects. Each device has its own web interface through which it is configurable after you connect to it via a web browser on a local network. The devices use the ESP8266 chip. I purchase the finished modules on AliExpress for about 2 euros per piece, and for the power supply I use the cheapest mobile phone chargers. Increase the voltage if necessary using cheap DC / DC converters.

Each device with the ESP8266 module, unconfigurable, provides its own "WiFi Hotspot", and after connecting, through the web interface it is possible to configure the device to connect to the local network.

1. LED lamp is dimmable

2. The thermometer only shows the measured temperature.

3. The thermostat, via a RELAY, can operate a heater (fan heater, boiler ...)

4. The router can be configured to send an external IP address to your e-mail so that you can access the Ujagaga IOT Router via the Internet and manage your thermostats, lamps, ... (Not yet completed)

5. "Lazy control" is an application for remote control of computer multimedia. This application is accessed via the computer's IP address on port 4211.

6. "Ujagaga IOT Browser" is an Android application through which you can list all devices on the local network from "Ujagaga IOT" projects. In this way, you do not have to have saved IP addresses of the devices, nor must they be static.

7. The NTP clock is synchronized over the Internet, so no adjustment is required. It uses stepper motors to drive minute and hour hands. The final clock design is up to the user.

Lazyfier - Remote controller for PC

I browsed the Google Play Store for a multimedial remote controller for PC with minimum number of commands and Linux support. All I found was too slow and unexceptable since I wanted to be able to pause a video or audio quickly when I get a Skype or phone call.

So I wrote a Python server and an Android app to do this. The App contains 2 button layouts and several different button backgrounds to choose from. Initially you simply run the server, which autoconfigures and repports the name of the server (computer name). You need to select this in the Android app setup to connect them. The server can be configured to use a password to prevent unauthorized access. It simulates a multimedia keyboard so it should support most players.

If you wish to test it, on the links below, you may download the Android APK and PC side server for either Linux or Windows. The sors code for the client and the server is also available

I have tested the client app on Android version 5.1 and 4.2. It should work on any version above 4.0.2.

Tips: Short click on the shutdown key will close the active window and a long click will shutdown the computer. It is similar with next and previous key, a short click will switch to next or previous playlist item, but a long one will seek. While using the cursor control function (MOUSE), the starting point is the middle of the screen when the phone is placed in a horizontal position. By tilting the phone you moove the cursor.

I have tested the server on Linux XUbuntu 16, 64-bit Windows7 and Windows 10.  

Linux version server install  Download Lazyfier server for Linux

Windows version server install  Download Lazyfier server for Windows

Android client  Download Lazyfier Client APK for Android  or  install from Google Play Store

Pay The Bills Reminder

I pay all my monthly bills via internet from my home computer. Ocasionally some bills arrive late and get forgotten. I wrote a desktop application where I can make a note of which bills I have payed as soon as I pay them. After a date configured for the checkout, if any of the bills is not payed, a popup notification informs of unpaid bills. By clicking the configuration button, a text file is opened which contains a list of bills which should be corrected according to your neads. A date of payment is added to bills that have been checked out. At the beginning of a month the configuration is archived and a new one is prepared with all the dates cleaned up so the process can be repeated for the current month. If you do not set a checkup date, the default one is 19-th.

You may download the application for Linux or Windows. The source code is also available.

Building a USB device

 

Disclaimer

The following is a summary of my modest experience in building hardware using Atmel micro controllers and software support for USB devices on Linux and Windows operating systems. The text is intended as a beginner's guide to making USB devices. I hope that it will save you time required for such a task. This guide does not contain everything you need to know about USB devices. I do not claim that my text is applicable to your specific problem, or that there will be no material damage by following these instructions. Use at your own risk.

 

Introduction to the USB standard

USB device may be of class HID, CDC, Mouse, HUB, a specific class of your own... I used the CDC, and HID the most.

A CDC device is easy to communicate to. On a linux operating system it is detected without a problem as a serial device type "/dev/ttyACM0" but on windows a driver needs to be prepared so it can be detected as, say "COM4". At this point, I guess this sounds complicated, but fortunately there are programs that can do this for you. A CDC device can be used from serial port applications such as GTKTERM, HTERM, PUTTY...

HID device requires writing your own program for communication because neither the operating system nor the third party programs know how you implemented your communication protocol. This will depend on the micro controller firmware. I found it easiest to write my application in Python programming language because it is very well documented and easy to use.

If you select a device of type mouse or keyboard, the operating system will install the driver it already has and take control of the device. To use it from your program, you have to find a way to tell the operating system to release the device so that you can controll it. i have not done this yet, so I can not help you.

Each USB device must have a so-called descriptor to inform the host of the details of the device. If the descriptor is such that the device is not identified as a standard mouse, keyboard or some other standard device, windows will ask for drivers. You can omit the descriptor in which case windows will not repport anything, but you will have to install the appropriate driver manually.

If you use Microchip's controller and any of their libraries, MLA or Harmony, you can usually find a driver that has already been signed. If you use a higher class Atmel microcontroller, it is similar, but if you use a cheaper controller like attiny, it does not have a USB interface, so you can achieve USB functionality using VUSB library for software emulation. VUSB library comes with ready-made examples that are quite simply modified.

 

CDC configuration

While it is easiest to communicate with, because you do not need to write an additional application but use one of available programs to communicate through the serial port, on windows operating system it can create a lot of problems if it has been implemented using VUSB library. The driver that can be found on the Internet (http://www.recursion.jp/prose/avrcdc) is not digitally signed. To use the driver on the 64-bit version of Windows, you must hold down the F8 key while booting and in the boot menu, select "Disable driver signing enforcement". Of course, you can also use some other program to do this. On 32-bit version of Windows 7, while installing the driver, you should be able to simply click "Install anyway", when windows repports that it is not digitally signed.

On a linux OS, CDC device simply works. Note, however, CDC is infact treated as a modem, so it can take up to 10 seconds before the modem manager refreshes the devices so your device becomes available.

 

HID configuration

Although there are not many readily available applications for communication wid a HID device, it is relatively easy to write your own application. There are plenty of examples for HID communication, Python has modules for this. What is important to know is that there are a lot of different libraries to work with HID devices (writing drivers and applications that uses that driver) and here I will mention only LibUSB because it provides the simplest solution.

On a linux operating system, libusb library comes pre-installed and does not couse any problems with using the driver. It is enough to write an application that communicates via libusb with your device.

On Windows, the situation is somewhat more complicated. You need to install libusb-win32 package. It comes with a InfWizard that will help you create digitally signed driver for windows.

 

Hardware Identifiers

Each USB device has a vendor id(Vid) and a product id (Pid). They are configured in the microcontroller firmware. Examples come with some free identifiers. You can change them, but the problem occurs if it is the same as some other device you use. Therefore, certification of identifiers is something you pay for in order to maintain a unique table of devices so operating systems know which drivers to use. This makes development of commercial devices cost somewhat more, but for a hobby device that is for your personal use only, leave Vid supplied with the example, and feel free to change the Pid. In this way you will make sure that you are not using an identifier of a commercial device and you can create multiple devices for personal use.

 

Writing The Application

As an example of building USB devices you can use my USB pulse generator with a complete project available free of charge. After building the device, you need to take care of the driver. If you decide to have a CDC class device, you only need to run a program for serial communication (HTERM, PUTTY, GTKTERM, ...), and if you decide to use a HID class device, it will be necessary to write an application to help you contoll it.

The available examples of the firmware, usually come with an example application in the C programming language. I found Python to be the simplest because it has modules for this, so writing an application requires much less lines of code. Here I will list only the most important code snippets to help you shortene the time needed to establish communication with your device.

 I used python2.7, and some basic code would look like this:

from usb import core, util

VENDOR_ID = 0x16c0
PRODUCT_ID = 0x05dc
dev = None
dev_status_changed = False


def connect_to_dev():
    global dev
    global VENDOR_ID
    global PRODUCT_ID

    dev = core.find(idVendor=VENDOR_ID, idProduct=PRODUCT_ID)

    if dev is not None:
        dev.set_configuration()


def query_device(msg, value=0):
    global dev
    global dev_status_changed

    REQUEST_TYPE = 0x20
    HID_SET_PROTOCOL = 0x0b

    if dev is None:
        connect_to_dev()
        if dev is None:
            return None
        else:
            dev_status_changed = True

    cfg = dev.get_active_configuration()
    endpoint = cfg[(0, 0)][0]

    result = None

    try:
        dev.ctrl_transfer(REQUEST_TYPE, HID_SET_PROTOCOL, (value << 8) | msg, 0, 0)
        response = dev.read(endpoint.bEndpointAddress, 1)
        result = response[0]
    except core.USBError as e:
        print e

    # release the device
    util.release_interface(dev, endpoint)
    if result is None:
        if dev is not None: 
            dev = None

    return result


my_msg = 0xAB
my_value = 0xCD

print query_device(my_msg, my_value)

Workspace switcher

At home and at work I use linux, Xubuntu with Xfce desktop. It has options to use multiple workspaces, but it can be difficult to distinguish between them. I wrote a shell script to switch between workspaces and change panel color for better distinguishing. Just call the shell script with the number of desired workspace as a parameter.
Example: wswitch 1
to switch to workspace 1 and set bckgnd1.png as background. Number of workspace is zero based, so you have workspace 0, 1, 2,... bckgnd0.png, bckgnd1.png,... are used to set background image. You may change them according to your preferences.

The script relies on wmctrl package, so I made a debian package to install this dependency as well. The source and the debian package for installation is available on my Github repository. Previously mentioned images for panel appearance are located, after installing the debian package, in your "HOME" folder in subfolder ".wswitch".

Shellmail

Shellmail is an automation script to send a quick e-mail notification.

Sometimes I have to wait a long time for a process to finish, so as a conveniance, I setup the process to send me an e-mail when it is done.

On linux, you have few options to do that and they all include a configured smtp server. It takes some time and a lot of experimenting to figure out all the parameters to configure to get this working,
so this script has a pre-defined smtp settings for g-mail and you can easily change them to your preferences. After you have setup all the necessary stuf asked by this script after installation,
you only need to send an email by executing shellmail command.

usage: shellmail [ < switch > < value > ] [  <"Optional message text" or path to text file > ]

Examples:

shellmail (sends a blank email to a predefined recepient with a predefined subject)

shellmail "Some message text" (sends the specified message to the predefined recepient)

shellmail -r your.name@gmail.com "Some text" (sends specified message to specified recipient)

shellmail -c (opens configuration files)

shellmail -h (prints help)

 

The source and debian package are available on my Github repository.

Quiet At Work

There are plenty of Android apps on this subject, but they do not seem to work on my new phone, so I wrote my own. Location detection was unreliable on my previous phone, but WiFi is reliable enough for an app to detect when I am at work. Using detected WiFi networks, this app switches the audio profile to silent so I do not bother my coleagues. You may dowload it fron the play store. The sorce code is available on Github.

Share Screen

Ocasionally I need to share my screen with a coleque running his PC on the same network. I wrote a python script to do this. It works on Linux, Windows and should work on Mac.

All you need to do is to run the script like

python3 sharescreen.py

or if you wish to specify the port like 89000:

python3 sharescreen.py 89000

The script will install dependencies automatically. on windows, you might need to run it a couple of times untill all dependencies are installed.

After that, you simply need to open a web browser on another computer and go to IP address on port you specified like:

192.168.0.10:9000

 

Simple Dynamic DNS Service

This is a python based, one file, single user, dynamic DNS server. I wrote it for my own home projects, so I can access my home router via internet.

The point of DDNS is that your routers external IP sometimes changes. This server provides a mechanisam to access the current IP address via link you set yourself.
This server can be hosted on an external service or your own machine.

What you have to know to use it is the server secret key, which is a password like, at least 8 (recomended, but not required) characters long, alphanumeric string. Eg. qwerty123.

To add or update a sub-domain, make a get request to something like:
https://mysubdomain.thisddnsservice.com/?secret=qwerty123

Now you can access your device at: https://mysubdomain.thisddnsservice.com

You can download the source code from github.