#### cykrus

Joined Oct 1, 2012
4
Hello all,

I am very new to the micro-controller world so bare with me.

I want to make a remote control to be able to send data between t PIC's (16f628). I know that there are already products out there (i have tested h12e/d rd600 d/e and they work great). My scope is to learn and play with PIC and not to use already made products

Before this project i did the "flash led" type of tutorials to learn a little bit about PIC's. I have a picckit3 programmer and I'm using the PIC C compiler.

Environment setup :
I have 2 16f628 pic's and a set of 434 Mhz RX/TX. I also have a max 232
connected to my serial port and receiver PIC in order to be able to debug data. At the hardware level have no problems setting it up.

Software setup:

The idea is that I want to be able to send a data package (comming from input pins) from PIC1(connected to the TX 434) to PIC2(connected to rx 434).

An here comes the code I have already wrote. Again ... this is my first real program so bare with me

DECODER

Rich (BB code):
#include <16F628.h>
#fuses INTRC_IO, NOLVP, NOWDT, PUT, BROWNOUT
#use delay(clock=4000000)
#use rs232(baud=19200, xmit=pin_B2, rcv=pin_B1)

void display_binary(int c){
int i;
i = 8;
do
{
if( c & 0x01 )
{ putc('1'); }
else
{ putc('0'); }

c >>= 1;  i--;
} while(i);
}

int sync(int a){
int found;
int string;
int bit;

int original;

original = a;

do{
a = original;
found = 0; // found the string
string = 0x00;

do{
if( input(PIN_A0) ){
bit = 0x01;
}
else{
bit = 0x00;
}
string = string | bit;
string <<= 1;

if( ((a & 0x01) ^ bit ) == 0 ){ // right bit == input
a >>= 1; // shift 1 position right
}
else{
return 0; // error
}

if( a == 0x00){
found = 1;
}

delay_us(500); // wait until next bit

}while( found == 0 );

}while( found == 0 );

return 1;
}

int getdata(){

int string = 0x00;
int i;

for(i=0;i<8;i++){
string <<= 1;
if( input(PIN_A0) ){
string |= 0x01;
}
else{
string |= 0x00;
}
delay_us(500);
}

return string;
}

void main(void) {

int prev, k, i;
unsigned int data;

while(1) {

k=0; // until i get 3 time the same result
do{

i=0;
do{
if( sync(0xAB) == 1 ){
i++;
delay_us(500);
}
else{
i = 0;
}
}while(i<3);

data = getdata();

if( k > 0 && data != prev) k=1; // reset
else k++; // one more good result

prev = data; // previous result used in the next loop

}
while(k<3);

if( data == -1 ) output_high(PIN_A2);
if( data == 63 ) output_high(PIN_A1);

printf("Found %d = ", data);
display_binary(data);
printf("\r\n");

delay_ms(250);
output_low(PIN_A2);
output_low(PIN_A1);
}

}
ENCODER

Rich (BB code):
#include <16F628.h>
#fuses INTRC_IO, NOLVP, NOWDT, PUT, BROWNOUT
#use delay(clock=4000000)

void send1(){
output_high(PIN_A0);
delay_us(500);
output_low(PIN_A0);
}
void send0(){
output_low(PIN_A0);
delay_us(500);
output_high(PIN_A0);
}

void sendbyte(int x){
int i=8;
do{
if(x & 0x01){
send1();
}
else{
send0();
}
x >>= 1;
i--;
}while(i);
}

main() {

while(true) {
if(input( PIN_B0) ){
// sync
sendbyte(0xAB);
delay_us(500);
sendbyte(0xAB);
delay_us(500);
sendbyte(0xAB);
delay_us(500);
sendbyte(0xFF);
delay_us(500);

}
else if(input( PIN_B1) ){
// sync
sendbyte(0xAB);
delay_us(500);
sendbyte(0xAB);
delay_us(500);
sendbyte(0xAB);
delay_us(500);
sendbyte(0xFC);
delay_us(500);
}
}
}
The idea is the encoder is sending 3 bytes (AB) as a sync (in order to align it with the RX) and then it send a byte of data depending on which pin B0 or B1 is high. The decoder searched for the 3 sync packages and then reads the byte (I'm reading it until i get 3 times the same value .. as i have experienced some errors due to radio noise i guess). Everything work so far but I'm sure it's not the perfect way to do it.

My questions are :

1. I have set a delay of 500us between bits and bytes as well. Is this correct ? What should be an optimal value ?
2. I coded 2 function for sending 1 or 0 bits. Is there another way to send directly a full byte to a pic PIN ?
2a. I have seen that in manchester it says that 1 is 0to1 transition and 1 is 1to0 ... does this mean that for sending a 1 I should do the following code ?
Rich (BB code):
output high;
delay 250us;
output_low;
delay 250us
How do i read this data (from port) on the other end ?

3. I have studied for 1 week a lot about the manchester encoding, i have understood how it works but i dont know how to apply it to hardware. Meaning how to I put the bits on the PORTS and how do i read them ? What is the delay between bits ? I searched a whole week but did not find any c sample of this ... only the manchester encoding process.

4. Is the way that i'm reading data from 434RX correct ? I have setup on both tx and rx same timing (delays between bits) and this is the way i "sync" .. is there another way do to this ?

Please feel free to correct/adjust my code and tell me what do I do wrong.

I want to learn and experimenting is for me the best way to do this.

Thanks,

#### cykrus

Joined Oct 1, 2012
4
Another question just came into my mind. The way that i'm syncronising the encoder/decoder is my seting the same delay between bits. Now my question is this ... how much time does it take to execute operations between sending bits ? For example is the encoder has a code like

Rich (BB code):
output high
delay 10us
output low
delay 10us
and the decoder has the code

Rich (BB code):
read input
delay 10us
<=== other 10 instructions come here
delay 10us
How much does it take for the "10 instructions" to execute ... can that cause a delay and with the 10us added on top the second "input" would no longer be aligned with the encoder's timing ?

How to solve this issue ... I suppose there is a way with the clock ? ... like in the so if we say "we'll meet there in 10 minutes" ... it is not so accurate as saying "we'll meet there at 2:50 PM" .. right ?

#### cykrus

Joined Oct 1, 2012
4
OOps ... i did some more reading and it looks like my code reinvented the wheel ))) ... sorry for that ... i just discovered ... "USART" ...

It looks like my code for sending/receiving bits is a "stoneage" version of USART ...

#### cykrus

Joined Oct 1, 2012
4
So .. after another day spent on forums i got the idea. I am using the UART and I have learner about all the registeres and bits for the rx buffer, error, etc etc. Great stuff ...

So I managed to implement a fully working link with a 4 bit address and 8 bit (can be extended to 10 - two pins are still left as rx/tx for the wireless link ) data between 2 pic16f628.

Next question just for fun ... can i save one more pin ? Is there a way when init the UART to only assign a pin (the tx) and rx to leave it undefined OR assigning it to some kind of NULL ?