AvcLan sniffer (Toyota media devices link protocol, using to communicate between headunit, amplifier, dsp, cd-changer etc)

Dependencies:   mbed-rtos mbed

Fork of rtos_basic by mbed official

main.cpp

Committer:
nn1317
Date:
2014-10-14
Revision:
7:164b5f80b483
Parent:
3:c92e21f305d8

File content as of revision 7:164b5f80b483:

#include "mbed.h"
#include "rtos.h"

DigitalOut led1(P3_25);     //leds are inversed!
DigitalOut led2(P3_26);     //leds are inversed!
DigitalOut transmitter(P0_6);
Timeout transmitterTimeOutControl;

DigitalIn receiverIn(P0_5);
int previousReceiverState = 0;
Timer receiverTimer;

#define RING_BUFFER_LENGTH 500

#define PREAMBULA_MINIMUM_LENGTH 150
#define PREAMBULA_MAXIMUM_LENGTH 200
#define BIT_0_MINIMUM_LENGTH 27

#define PACKET_LENGTH_IN_BITS 94

unsigned short ringBuffer[RING_BUFFER_LENGTH];
int ringBufferWriteIndex=0, ringBufferReadIndex=0;

Serial pc(P0_2, P0_3);

void parseAvcPacket(int fromRingIndex, int toRingIndex)
{
    int bitIndex = 0, blockStartLengthIndex = 0;
    unsigned short blockBits = 0x0000;
    for (int ringIndex = fromRingIndex; ringIndex != toRingIndex; )
    {
        int us_count = ringBuffer[ringBufferReadIndex];             
        
        if (us_count >= PREAMBULA_MAXIMUM_LENGTH)
        {
            pc.printf("\r\nWRONG %d us");
            break;
        }
        else if (us_count >= PREAMBULA_MINIMUM_LENGTH)
            pc.printf("\r\n");
        else 
        {
            unsigned short bit = (us_count > BIT_0_MINIMUM_LENGTH) ? 0 : 1;
            blockBits |= (bit << blockStartLengthIndex);
                
            int outInBlockLength = 8;//1, 4, 8, 12
            if ((bitIndex == 0) || (bitIndex == 13) || (bitIndex == 26) || (bitIndex == 27) || (bitIndex == 32) || (bitIndex == 33) || 
                (bitIndex == 42) || (bitIndex == 43) || (bitIndex == 52) || (bitIndex == 53) || (bitIndex == 62) || (bitIndex == 63) || 
                (bitIndex == 72) || (bitIndex == 73) || (bitIndex == 82) || (bitIndex == 83) || (bitIndex == 92) || (bitIndex == 93))
                 outInBlockLength = 1;
            else if (((bitIndex < 13) && (bitIndex >= 1)) || ((bitIndex < 26) && (bitIndex >= 14)))
                outInBlockLength = 12;
            else if ((bitIndex < 32) && (bitIndex >= 28))
                outInBlockLength = 4;
            
            if (blockStartLengthIndex >= outInBlockLength)
            {
                if (outInBlockLength == 1)
                    pc.printf("%d ", blockBits);
                else if (outInBlockLength == 4)
                    pc.printf("%X ", blockBits);
                else if (outInBlockLength == 8)
                    pc.printf("%X ", blockBits);
                else if (outInBlockLength == 12)
                    pc.printf("%X ", blockBits);
                    
                blockStartLengthIndex = 0;
                blockBits = 0x0000;
            }

            bitIndex ++;            
            blockStartLengthIndex ++;
        }
            
        ringIndex = (ringIndex+1) % RING_BUFFER_LENGTH;        
    }
}

void serialCommunicationThreadFunction(void const *args)
{
    pc.baud(115200);
    pc.printf("\r\nAVC-Lan sniffer is ON\r\n\r\n");
    
    led1 = 1;

    while (true) 
    {
        led1 = (ringBufferWriteIndex == ringBufferReadIndex);

        int packetEndIndex = (ringBufferReadIndex+1) % RING_BUFFER_LENGTH;
        int packetBitLength = 0;
        for (; ringBufferWriteIndex != packetEndIndex; )
            if ((packetBitLength == PACKET_LENGTH_IN_BITS) || ((ringBuffer[packetEndIndex] >= PREAMBULA_MINIMUM_LENGTH) && (ringBuffer[packetEndIndex] < PREAMBULA_MAXIMUM_LENGTH)))
            {
                parseAvcPacket(ringBufferReadIndex, (packetBitLength == PACKET_LENGTH_IN_BITS) ? packetEndIndex : (packetEndIndex-1));
                break;
            }
            else
            {
                packetEndIndex = (packetEndIndex+1) % RING_BUFFER_LENGTH;
                packetBitLength ++;
            }
    }
}

int main()
{
    Thread serialCommunicationThread(serialCommunicationThreadFunction);

    receiverIn.mode(PullUp);

    receiverTimer.reset();
    led2 = 1;

    while (true) 
    {
        if (receiverIn != previousReceiverState)
        {     
            led2 = 0;
            if (receiverIn)
            {
                receiverTimer.reset();
                receiverTimer.start();
            }
            else
            {
                receiverTimer.stop();
                int us_count = receiverTimer.read_us();                
                ringBuffer[ringBufferWriteIndex] = us_count;
                ringBufferWriteIndex = (ringBufferWriteIndex+1) % RING_BUFFER_LENGTH;
            }
                
            previousReceiverState = receiverIn;
            led2 = 1;
        }
    }
}