03:46 pm on Dec 29, 2013 | read the article | tags: hobby, raspberry
the love for gentoo and the spare time during this winter holidays made me update my minimal raspberry pi gentoo image. the image includes:
here’s the download link. enjoy! =) gentoo-3.10.25-blackcat-1.0.img.gz (sha1: d5560f81e43361a7e99db6e7d42e67d4446b0b7b)
12:11 am on May 3, 2013 | read the article | tags: hobby, raspberry
a few details on running gentoo-3.8.8-cat-0.8.img.gz on your raspberry pi:
i’m thinking to build an arduino interface to protect the pi’s GPIO and to extend the functionality using the serial port. don’t know when i’ll have time to do that, but it’s in my plans.
09:58 pm on Apr 28, 2013 | read the article | tags: hobby, raspberry
i love gentoo. mostly for its ability to be small and tight on the machine running it. so, here it is. a small gentoo distro (around 121Mb) that includes the following:
the kernel:
downloads:
references:
11:10 pm on Nov 1, 2012 | read the article | tags: hobby
for a week or so i’m searching the internet for a simple example (that can be easily expanded) on how to use the pic32-pinguino-otg with a UEXT connected enc28j60 module (both from olimex). and of course i didn’t wanted to use the “universal” microchip tcp/ip stack that requires MPlab. after digging quite a lot trough the pinguino repositories, i managed to compile a set of working header files (which you can find here) and a small program from which you can ping your boards. for the library to work, copy it under %pinguino/p32/include/pinguino/libraries/ethernet, where %pinguino is the path to your pinguino installation folder. i used pinguino X.3 and it compiled fine.
/*----------------------------------------------------- Author: --<> Date: 28/Oct/2012 Description: -----------------------------------------------------*/ #include <ethernet/ip_arp_udp.h> #define BUFFER_MAX 224 static u8 buf[BUFFER_MAX+1]; // the received message u16 len; // the length of the received messages void setup() { // put your setup code here, to run once: // this is the enc28j60 ip address u8 myip[4] = { 192, 168, 2, 2 }; // this is the enc28j60 mac address u8 mymac[6] = { 0x02, 0x04, 0x08, 0x10, 0x12, 0x14 }; init_ip_arp_udp (mymac, myip); enc28j60Init (mymac); } void loop() { len = enc28j60PacketReceive(BUFFER_MAX, buf); CDC.printf("received! len: %d\n", len); if (len == 0) { return; } if(eth_type_is_arp_and_my_ip(buf, len)) { make_arp_answer_from_request(buf, len); return; } if(eth_type_is_ip_and_my_ip(buf, len)==0) { return; } if(buf[IP_PROTO_P]==IP_PROTO_ICMP_V && buf[ICMP_TYPE_P]==ICMP_TYPE_ECHOREQUEST_V) { // the ping reply make_echo_reply_from_request(buf, len); return; } }
09:12 pm on Sep 23, 2012 | read the article | tags: hobby
recently i had a problem. i needed to build a wireless PIR sensor that could be powered by a LiPo 1400mAh battery. seems like a lot of juice, but thinking that the wixel draws usually almost 30mA and a mangled PIR sensor 8mA, the sensor would have to be recharged every 1.5 days. not a practical approach. through some neat hack i managed to send the wixel in sleep mode, making it draw less than 100uA, but still had the power hungry PIR sensor.
today i managed to solve this problem also. using a cheap (~$15) PIR sensor with a nice housing and a few components i managed to bring the PIR sensor as low as 1.6mA (measured), making the battery last for 34 days. here’s how:
first remove the PIR element. it’s quite big component, encased in metal and with a window for sensing IR radiation. be careful when removing it as it is quite a sensitive component! then gather the components and build this schematic:
components list:
IS1 is the PIR element. this component was on my Eagle library and matched the dimensions of the one i recovered.
R1, R3 = 47K
R2 = 18K
R4, R8 = 1M
R5 = 1K
R6, R7, R9 = 100K
R10 = 330K
C1, C7 = 10uF (there is no mistake! C7 is 10uF but can be polarized. i used tantalum capacitors)
C2, C3 = 4.7uF
C4, C5, C6 = 10nF
IC1A, IC1B = TL082
JP1 = a 3 pin connector in which 1 = +3V3, 2 = signal (connect to wixel P1_0), 3 = GND
JP2, JP3, JP4 = 2 pin connectors as there’s always a good idea to serve power to other devices
notes:
the R9, R10, C7 group sets the sensitivity of the PIR sensor. this setup worked for what i wanted but trust me, it took about 3 hours of testing to get to those values and configuration. the interrupt on P1_0 of the wixel should be configured for raising edge, not falling. R10 is needed to lower the IC1B output potential below the interrupt threshold. an IR event sends the IC1B output close to 3.3V followed by a drop to almost 0V then back to almost 1.65V (this is the value you should have when idle). with R9/R10 the idle voltage is close to 1.26V making the interrupts stable. setting R10 higher, moves this point close to 1.65V when the interrupts are unstable. making it lower decreases the sensitivity. i don’t recommend getting under 56K (standard value) as the interrupts cannot be triggered anymore.
bibliography:
i drew inspiration from Micropik’s D203B PIR element datasheet.
10:18 pm on Sep 22, 2012 | read the article | tags: hobby
don’t know if you have any idea what this is, but i love the wixel. it’s a CC2511F32 based device that works basically like every arduino except that it has a embed wireless transceiver. i got mine from watterott. the wixel is a nifty little device, good for connecting sensors to a PC, both wired and wireless. the problem for the wireless approach is that the device is power hungry 30mA is quite a lot for a battery powered app. but luckily, CC2511F32 is made by texas instruments that addressed this issue: it has a sleep mode in which it consumes less than 1uA.
here’s a small code i’ve wrote to test this sleep mode, based on blink led. it blinks the led 10 times, then powers down and waits for a falling edge on P1_0 (remember to connect this pin with a resistor to 3V3 in order to make the device sleep, otherwise P1_0 is quite sensitive).
#include <wixel.h> #include <usb.h> #include <usb_com.h> #include <stdio.h> int32 CODE param_blink_period_ms = 500; int32 CODE param_count = 20; // counting 20 changes of the red led state, then go to sleep uint32 count = 0; // the actual counter uint32 lastToggle = 0; /* catch interrupts on P1INT */ ISR (P1INT, 0) { /* clearing the CPU interrupt registers */ /* 1. first the general interrupt register, IRCON2 */ IRCON2 &= ~0x08; // clear IRCON2.P1IF /* 2. followed by the P1 interrupt register, P1IFG */ P1IFG &= ~0x01; // clear P1IF0 /* not related to the interrupt itself, but to the */ /* sleep mode: clear SLEEP.MODE flag */ SLEEP &= ~0x03; // clear SLEEP.MODE /* disable interrupt only for P1_0 */ P1IEN &= ~0x01; // clear P1_0IEN /* wait, disabling interrupts on P1 also :) */ IEN2 &= ~0x10; // clear IEN2.P1IE } /* the function that puts the system to sleep */ /* i've chosen PM3 as i don't need a timer wake-up event */ void putToSleep () { /* make the P1_0 a input pin */ P1DIR &= ~0x01; // P1_0DIR = 0 -> input /* clear any interrupt flags. see above for details */ IRCON2 &= ~0x08; // clear IRCON2.P1IF P1IFG &= ~0x01; // clear P1IF0 /* set the interrupt enable flag on P1_0 */ P1IEN |= 0x01; // P1_0IEN = 1; /* set the type of interrupt: 0=rising edge; 1=falling */ PICTL &= ~0x02; // PICTL.P1ICON = 0 /* set the interrupt enable flag for the entire P1 */ IEN2 |= 0x10; // IEN2.P1IE = 1; /* enable global interrupts */ IEN0 |= 0x80; // IEN0.EA = 1; /* the sleep mode i've chosen is PM3 */ SLEEP |= 0x03; // SLEEP.MODE = PM3 /* idling the CPU - required in the manual */ if (SLEEP & 0x03) PCON |= 0x01; // PCON.IDLE = 1; } void updateLeds() { usbShowStatusWithGreenLed(); LED_YELLOW(0); if (getMs() - lastToggle >= param_blink_period_ms/2) { LED_RED(!LED_RED_STATE); lastToggle = getMs(); /* the piece of code that counts and if the counter */ /* hits the limit, puts the system to sleep */ count++; if (count == param_count) { count = 0; /* here the blinking freezes, waiting for a */ /* falling edge on P1_0 */ putToSleep(); } } } void main() { systemInit(); usbInit(); while(1) { boardService(); updateLeds(); usbComService(); } }
09:22 pm on Sep 18, 2012 | read the article | tags: hobby
pentru prima dată voi participa la un eveniment dedicat online-ului. webstock 2012. am primit chiar astăzi invitația de la cristian manafu. m-am înscris din curiozitate și din dorința de a cunoaște (cu puțin noroc) personal oamenii ale căror gânduri le citesc în fiecare dimineață. revin cu detalii.
09:28 pm on Jul 29, 2012 | read the article | tags: hobby
as a part of my PhD. studies i needed a simple interface to a central heating unit (CHU). searching the internet i found that most CHU are slave devices that use OpenTherm protocol for communication. i will bother you with that in a future post. for now, OpenTherm uses the Manchester code for sending and receiving information. as recently i’ve switched from arduino to pinguino (still using arduino for my work with students), here’s a small library that i use to decode the OpenTherm messages, that is versatile enough to be used for any Manchester code codec. it worked with a PINGUINO MX220 from Olimex. the tolerance for the bit timing is quite good: it correctly received data with bit lengths from 880uS to 1320uS. for other ranges tweak the defined constants.
// the code bellow is provided "as-is" with no warranty whatsoever // also, this is a sketch and should be treated likewise /* half the bit length */ #define OTHRM_BIT_TX0 500 /* threshold in microseconds for bit detection. it should be larger than the fastest transition time, yet it should consider the clock tolerance and the speed of the CPU. for PINGUINO 32MX220 this worked */ #define OTHRM_BIT_RX0 300 /* maximum length of a bit, in microseconds */ #define OTHRM_BIT_RX1 1000 #include <delay.c> /* the OpenTherm frame has 32 bits. for 8 bit processors, use an array */ volatile u32 OTHRM_FRAME; /* this function sends the OTHRM_FRAME data through "pin" */ void othrm_tx (u8 pin) { u8 c = 0; /* start bit "1" of OpenTherm */ digitalWrite (pin, HIGH); Delayus (OTHRM_BIT_TX0); digitalWrite (pin, LOW); Delayus (OTHRM_BIT_TX0); /* actual data */ for (c = 0; c<32; c++) { if ((OTHRM_FRAME >> 31) == 1) { digitalWrite (pin, HIGH); Delayus (OTHRM_BIT_TX0); digitalWrite (pin, LOW); Delayus (OTHRM_BIT_TX0); } else { digitalWrite (pin, LOW); Delayus (OTHRM_BIT_TX0); digitalWrite (pin, HIGH); Delayus (OTHRM_BIT_TX0); } OTHRM_FRAME <<= 1; } /* stop bit "1" of OpenTherm */ digitalWrite (pin, HIGH); Delayus (OTHRM_BIT_TX0); digitalWrite (pin, LOW); Delayus (OTHRM_BIT_TX0); } /* receiving data from pin "pin". the data will be found in OTHRM_FRAME */ void othrm_rx (u8 pin) { u8 s = 1, c = 0; u16 m = 0, t = 0; OTHRM_FRAME = 1; /* wait for the begining of the start bit. i need this. for non-blocking operation you should include a timer with a timeout. */ while (!digitalRead(pin)); for (c = 0; c<33; c++) { OTHRM_FRAME <<= 1; t = 0; while ((s == digitalRead(pin)) && (t < OTHRM_BIT_RX0)) { t++; Delayus(1); } s = digitalRead(pin); OTHRM_FRAME |= !s; t = 0; while ((s == digitalRead(pin)) && (t < OTHRM_BIT_RX0)) { t++; Delayus(1); } s = digitalRead(pin); } }
12:15 pm on Jan 28, 2012 | read the article | tags: hobby
i’ve got a bunch of sensors form my PhD. thesis. i won’t bother you with the details =). unfortunately i wasn’t very inspired in my choosing and i ended up with a bunch of accurate, but hard to access sensors. the ones i’m talking about are MPL115A1, SHT15 and TSL230R all from my favorite provider watterott.
i’ve roamed the internet for a while to find myself some Arduino libraries to access the sensors but failed to find what i wanted. so here’s what i came up with MPL115A1 Arduino library, SHT15 Arduino library and TSL230R Arduino library. the code is provided “as-is” and the work is based on roaming drone’s TSL230R tutorial, jim lindblom’s sparkfun MPL115A1 example code and nathan seidle’s sparkfun SHT15 example code.
tomorrow i’ll update this post with an example code and some wiring diagrams.
03:30 pm on Dec 20, 2011 | read the article | tags: hobby
yesterday, i’ve posted my wrapper library for the windows COM port with the promise of posting the actual C program that uses it. to compile it you need mingw (see here my tutorial on how to get it up and running). the program is simple and writes in the text.txt file whatever it receives on the serial interface, but no more than MAXLINES lines (in this case, 10 lines). you need to save the previous code as “serial.h” in the same directory as the code below. then, compile it and that’s it! =)
ask whatever questions here, and i will answer.
#include <stdio.h> #include <windows.h> #include "serial.h" // the number of lines read from the serial interface. // good for data acquisition for a specified amount of time. #define MAXLINES 10 int main (int argc, int ** argv) { HANDLE comPort; FILE * f; char buffer[32]; unsigned short int readbits = 0; unsigned long int lines = 0; unsigned short int c; // my COM port is COM15. be sure to change it accordingly if ((comPort = openSerialConsole("\\\\.\\COM15")) == (void *) NULL) { printf ("Error: COM Port!\n"); return 1; } // open the file "text.txt". change it for a different file f = fopen ("test.txt", "w+"); // read online MAXLINES lines while (lines < MAXLINES) { // readbits is the number of bytes read from the COM port while ((readbits = readFromSerialConsole(comPort, buffer, 32)) != 0) { // a good thing to check that the readbits+1 character marks the end // of the string. saves you from "Segmentation fault!" errors buffer[readbits] = 0; // check buffer for ENDL character for (c = 0; c<readbits; c++) if (buffer[c] == '\n') { lines++; if (lines == MAXLINES) buffer[c] = 0; } // output to the standard IO, and printf("%s", buffer); // to the file fprintf(f, "%s", buffer); } } // close the file handle fclose (f); // close the COM port closeSerialConsole(comPort); return 0; }
aceast sait folosește cookie-uri pentru a îmbunătăți experiența ta, ca vizitator. în același scop, acest sait utilizează modulul Facebook pentru integrarea cu rețeaua lor socială. poți accesa aici politica mea de confidențialitate.