; ; Definitions ; .def temp1 = r16 ; Temporary register .def temp2 = r17 ; Temporary register .def temp3 = r18 ; Temporary register ; ; Test routine for Manchester Encoding / Decoding ; ldi temp1, 0 Test_Manchester_Coding: mov XL, temp1 call Encode_Manchester_RFLink call Decode_Manchester_RFLink dec temp1 brne Test_Manchester_Coding ; ; OK done ; ; ********************************************************* ; Function Encode_Manchester_RFLink ; ; Purpose: Encode one byte to a 2 byte manchester word ; ; Byte to be encoded in XL register ; Encoded word returned in X register (MSB in XH and LSB in XL) ; ; Encoding = 16 clocks = 2 us for 8 MHz Clock ; ; Encoding Algorithm in C: ; ------------------------ ; ms = (c & 0xAA) | ((~c & 0xAA)>>1); /* encode odd bits w/ their complements */ ; ls = (c & 0x55) | ((~c & 0x55)<<1); /* now even bits */ ; return ((ushort)ms << 8) | ls; ; ; ********************************************************* Encode_Manchester_RFLink: ; ; Save working registers ; push temp1 push temp2 ; ; Encode most significant part of byte (high nibble) ; mov temp1, XL ; 1 clock andi temp1, 0xAA ; 1 clock mov temp2, XL ; 1 clock com temp2 ; 1 clock andi temp2, 0xAA ; 1 clock lsr temp2 ; 1 clock or temp1, temp2 ; 1 clock mov XH, temp1 ; 1 clock ; ; Encode least significant part of byte (low nibble) ; mov temp1, XL ; 1 clock andi temp1, 0x55 ; 1 clock mov temp2, XL ; 1 clock com temp2 ; 1 clock andi temp2, 0x55 ; 1 clock lsl temp2 ; 1 clock or temp1, temp2 ; 1 clock mov XL, temp1 ; 1 clock ; ; Restore working registers ; pop temp2 pop temp1 ret ; ; ********************************************************* ; Function Decode_Manchester_RFLink ; ; Purpose: Decode a 2 byte manchester word o a one byte ; ; Manchester word to be decoded in X register (MSB in XH and LSB in XL) ; Byte will be returned in XL register ; ; Correct decoding: Carry is clear ; Wrong decoding: Carry is set ; ; Decoding = 6 clocks = 0.7 us for 8 MHz Clock, without error checking ; ; Decoding Algorithm in C: ; ------------------------ ; ms = (uchar)(mc >> 8); /* get ms byte from short */ ; if ( (ms & 0xAA) ^ ((~ms & 0x55) << 1) ) then error ; ms &= 0xAA; /* otherwise, valid data, so just clear complements*/ ; ls = (uchar)mc; /* now test even bits... */ ; if ( (ls & 0x55) ^ ((~ls & 0xAA)>>1) ) then error ; ls &= 0x55; /* valid, so clear complements */ ; return ms | ls; /* OR original odd and even bits back together */; ; ; ********************************************************* Decode_Manchester_RFLink: ; ; Save working registers ; push temp1 push temp2 push temp3 ; ; Decode MSB ; mov temp1, XH ; 1 cl andi temp1, 0xAA ; 1 cl mov temp2, temp1 ; 1 cl ; ; Test for error ; com XH andi XH, 0x55 lsl XH eor temp1, XH brne Decode_Manchester_RFLink_error ; ; Decode LSB ; mov temp1, XL ; 1 cl andi temp1, 0x55 ; 1 cl mov temp3, temp1 ; 1 cl ; ; Test for error ; com XL andi XL, 0xAA lsr XL eor temp1, XL brne Decode_Manchester_RFLink_error ; ; OR the even and odd bits back to one register ; or temp2, temp3 ; 1 cl mov XL, temp2 ; ; Clear carry for correct result ; clc brcc Decode_Manchester_RFLink_1 Decode_Manchester_RFLink_error: ; ; Set carry for incorrect result ; sec Decode_Manchester_RFLink_1: ; ; Restore working registers ; pop temp3 pop temp2 pop temp1 ret