Thinklight

Hupiprojekti täynnä C-koodausta ja reverse engineerausta

Teknologiat: C
Demo

Joskus vuosia sitten päätin hetken mielijohteesta tutustua matalamman tason Linux-koodaamiseen. Myös C-kieli tuntui jotenkin primitiivisen houkuttelevalta. Tarvitsin vain jonkun sopivan aiheen, koska päätön random-koodaus ei yleensä ole erityisen motivoivaa.

Pienen googlailun jälkeen löysin jostain internetin säläkaupasta pienen usb-liitäntäisen valon, joka palaa sitä kirkkaammin, mitä nopeammin näppäimistöä takoo. Spekseissa sanottiin laitteen käyttöön tarvittavan ajurin olevan vain Windowsille. Haa! Siinä oli hyvä tavoite: päätin koodata vekottimen toimimaan myös Linuxilla.

Kun laite saapui, ruuvasin sen ensi töikseni auki, jotta näkisin mitä sen sisällä on. Varsin yksinkertainenhan se oli – viisi lediä ja joku ohjainpiiri. Selkeästi siis kirkkauden säätö tapahtuisi sytyttämällä ledejä yksi kerrallaan palamaan. Mutta miten se tapahtuisi? Projekti oli luonteeltaan kaksiosainen. Sen lisäksi että piti kirjoittaa koodia, oli välttämätöntä selvittää laitteen toimintaperiaate ns. reverse engineeringillä.

Aloitin kirjoittamalla pohjakoodin ohjelmalleni. Käytännössä se oli standardin usb-kirjaston käyttöä, jonka avulla tunnistin lampun kaikkien järjestelmään kytkettyjen usb-laitteiden joukosta ja avadin yhteyden siihen. Lisäksi tein tarvittavat rutiinit ohjelman saattamiseksi daemon-muotoon.

Seuraavaksi tökkäsin lampun ensimmäiseksi Windows-koneeseen ja asensin mukana tulleen ajurin. Avasin usb-snifferin ja rupesin näpyttelemään näppäimistöä. Nauhoitin hetken aikaa tätä datavirtaa ja aloin analysoida sitä. Hetken tutkailun jälkeen aloin huomata säännöllisesti toistuvan seitsemän tavun ryppään: 0x55, 0x53, 0x42, 0x43, 0x00, 0x00 ja 0x02. Näiden perässä oleva kahdeksas tavu oli muuttuva lukema, joten päättelin sen olevan lampun kirkkautta säätelevä tavu.

Palasin takaisin C-koodini pariin, sillä nyt tiesin, mitä dataa laitteelle täytyy kirjoittaa. Pienen lisäanalyysin perusteella selvisi, että tuo kahdeksas tavu on itse asiassa bittikenttä, josta käytetään vain viittä alinta bittiä, yksi kutakin lediä kohden. Jos bitti on ylhäällä, ledi syttyy. Jos alhaalla, ledi sammuu.

Tästä eteenpäin koodin kirjoittaminen oli jokseenkin suoraviivaista. Tein loputkin tarvittavan rutiinit ledien sytyttämiseen ja sammuttamiseen sekä event loopin, joka huolehti lampun kirkkauden säätelystä näppäimistöaktiivisuuden mukaan. Tässä hain sopivan tahdin yksinkertaiseksi kokeilemalla, kunnes lampun toiminta tuntui mukavalta.

Myöhemmin tein kokeilun vuoksi pari lisärutiinia, jotka tarkkailivat näppäimistön sijaan hiirtä ja tiedostojärjestelmää.

Projekti oli tarkoitukseensa nähden käytännössä täydellinen. Onnistuin löytämään laitteen, jonka toiminnan selvittäminen oli juuri sopivan vaikeaa. Motivaatio säilyi, kun koko ajan joutui opettelemaan uutta, mutta missään vaiheessa ei niin sanotusti tullut seinä vastaan.


Kuva: TeroVesalainen / Pixabay