communication between Arduino and linux c++(odroid Ubuntu)

Hello arduino~

before saying...im eastern and not good at English...
so plz.... understand my English level....: )

im going to use ultrasonicwave sensor to receive distance value to arduino

and that value will send to C++

In c++ some algorithim will work and send signal to arduino to run dc motor and sub motor

this send, receive signal should work everytime while my car is working....

So! my question is how to receive data from arduino to linux
and receive data from linux to arduino

my base code of arduino is this....

// #include <Servo.h>

//Servo myservo; // 서보모터 선언

//int buzzer = 2;
//int motor_direction = 13;
//int motor_pwm = 11;
//int motor_break = 8;

int trigPin1 = 23; // 전방 우측 센서   -----> means foward right sensor....not much meaning
int echoPin1 = 22;
int trigPin2 = 25; // 전방 중앙 센서
int echoPin2 = 24;
int trigPin3 = 27; // 전방 좌측 센서
int echoPin3 = 26;
int trigPin4 = 48; // 후방 좌측 센서
int echoPin4 = 49;
int trigPin5 = 50; // 후방 중앙 센서
int echoPin5 = 51;
int trigPin6 = 52; // 후방 우측 센서
int echoPin6 = 53;


void setup()
{
  //myservo.attach(5); // 서보모터를 5번핀에 연결
  //myservo.write(90);  // 90'가 중심각도 여기서 +,- 30~31'가 조향임.
                      // 서보모터 회전정도를 정함 30~31이 최고임.

  Serial.begin(115200);
  // pinMode(buzzer, OUTPUT);

 // pinMode(motor_direction, OUTPUT);
 // pinMode(motor_pwm, OUTPUT);
 // pinMode(motor_break, OUTPUT);
  
  pinMode(trigPin1, OUTPUT);
  pinMode(echoPin1, INPUT);
  pinMode(trigPin2, OUTPUT);
  pinMode(echoPin2, INPUT);
  pinMode(trigPin3, OUTPUT);
  pinMode(echoPin3, INPUT);
  pinMode(trigPin4, OUTPUT);
  pinMode(echoPin4, INPUT);
  pinMode(trigPin5, OUTPUT);
  pinMode(echoPin5, INPUT);
  pinMode(trigPin6, OUTPUT);
  pinMode(echoPin6, INPUT);  
}

void loop()
{  
  digitalWrite(trigPin1, LOW);  
  digitalWrite(echoPin1, LOW);
  delay(2);          
  digitalWrite(trigPin1, HIGH);   
  delay(10);       
  digitalWrite(trigPin1, LOW);
  unsigned long duration1 = pulseIn(echoPin1, HIGH);
  float distance1 = duration1 /29.0/2.0;

  digitalWrite(trigPin2, LOW);  
  digitalWrite(echoPin2, LOW);
  delay(2);          
  digitalWrite(trigPin2, HIGH);   
  delay(10);       
  digitalWrite(trigPin2, LOW);
  unsigned long duration2 = pulseIn(echoPin2, HIGH);
  float distance2 = duration2 /29.0/2.0;
  
  digitalWrite(trigPin3, LOW);  
  digitalWrite(echoPin3, LOW);
  delay(2);          
  digitalWrite(trigPin3, HIGH);   
  delay(10);       
  digitalWrite(trigPin3, LOW);
  unsigned long duration3 = pulseIn(echoPin3, HIGH);
  float distance3 = duration3 /29.0/2.0;

  digitalWrite(trigPin4, LOW);  
  digitalWrite(echoPin4, LOW);
  delay(2);          
  digitalWrite(trigPin4, HIGH);   
  delay(10);       
  digitalWrite(trigPin4, LOW);
  unsigned long duration4 = pulseIn(echoPin4, HIGH);
  float distance4 = duration4 /29.0/2.0;

  digitalWrite(trigPin5, LOW);  
  digitalWrite(echoPin5, LOW);
  delay(2);          
  digitalWrite(trigPin5, HIGH);   
  delay(10);       
  digitalWrite(trigPin5, LOW);
  unsigned long duration5 = pulseIn(echoPin5, HIGH);
  float distance5 = duration5 /29.0/2.0;

  long duration6, distance6;    
  digitalWrite(trigPin6, LOW);  
  delay(2);          
  digitalWrite(trigPin6, HIGH);   
  delay(10);       
  digitalWrite(trigPin6, LOW);
  duration6 = pulseIn(echoPin6, HIGH);
  distance6 = duration6 * 17 / 1000;

  Serial.print("\nDistance1: ");
  Serial.print(distance1);
  Serial.print("cm\n\n");

  Serial.print("\nDistance2: ");
  Serial.print(distance2);
  Serial.print("cm\n\n");
  
  Serial.print("\nDistance3: ");
  Serial.print(distance3);
  Serial.print("cm\n\n");
  
  Serial.print("\nDistance4: ");
  Serial.print(distance4);
  Serial.print("cm\n\n");
  
  Serial.print("\nDistance5: ");
  Serial.print(distance5);
  Serial.print("cm\n\n");
  
  Serial.print("\nDistance6: ");
  Serial.print(distance6);
  Serial.print("cm\n\n");

   
  }

But i have no idea how to make code in linux(C++) to receive data from arduino

my question maybe so ideal....but please u guys are my hope
PLZ HELP ME! :frowning:

You could use the Code Block IDE and an add on called wxwidgets.

You can use a Arduino library call EasyTransfer.

http://www.wxwidgets.org/

I got EasyTransfer to work on the PC side, i have some code that will help when you get that far. I posted about it in another thread but got no interest.

This Python - Arduino demo should help get you started. It was created on Linux.

...R

EVP:
You could use the Code Block IDE and an add on called wxwidgets.

You can use a Arduino library call EasyTransfer.

http://www.codeblocks.org/

http://www.wxwidgets.org/

I got EasyTransfer to work on the PC side, i have some code that will help when you get that far. I posted about it in another thread but got no interest.

not me~
i installed codeblocks on my ubuntu and add an wxwidgets.... if u give me a link to that code..... i'll really graceful to use that code.... plz leave me a code link for me ㅠㅠ

Robin2:
This Python - Arduino demo should help get you started. It was created on Linux.

...R

hmmm...... im not good at python really a beginner..... and u mean i should learn python either...? lol.... :frowning:

kosh09:
and u mean i should learn python either...? lol.... :frowning:

When you know one programming language the others are relatively easy.

...R

Robin2:
When you know one programming language the others are relatively easy.

...R

that sounds familiar to me.... (from professor kk)
but make sense! thx for help!!!

Hi kosh09, there it is i've just copied and pasted it straight out of my project but you should be able to get it working easy enough.

The . file

#define EASYTRANSFER_H

#include <stdio.h>
#include <stdlib.h>
#include <stdint.h>
#include <windows.h>
//////////////////////////
#define details(name) (uint8_t*)&name,sizeof(name)

class EasyTransfer
{
    public:
        EasyTransfer();

void begin(uint8_t *, uint8_t);
//void begin(uint8_t *, uint8_t, NewSoftSerial *theSerial);
void sendData(HANDLE	hComi);
bool receiveData(HANDLE	hComi);
private:
void *_stream;//Stream *_stream;
//NewSoftSerial *_serial;
uint8_t * address;  //address of struct
uint8_t size;       //size of struct
uint8_t * rx_buffer; //address for temporary storage and parsing buffer
uint8_t rx_array_inx;  //index for RX parsing buffer
uint8_t rx_len;		//RX packet length according to the packet
uint8_t calc_CS;	   //calculated Chacksum
    protected:

    private:
};

#endif // EASYTRANSFER_H

the cpp. file

#include "EasyTransfer.h"

EasyTransfer::EasyTransfer()
{
    //ctor
}
///////////////////////////////////////////////////////////////////////////

unsigned char ReadData(HANDLE	hComi)
{
    unsigned char Buf[1];

    DWORD bytesRead;

    unsigned int toRead=1;

        if(ReadFile(hComi, Buf, toRead, &bytesRead, NULL) )
        {
           return Buf[0];
        }

    return 0;

}

///////////////////////////////////////////////////////////////////////////
bool WriteData(unsigned char *buffer, unsigned int nbChar,HANDLE	hComi)
{
    DWORD bytesSend;

    //Try to write the buffer on the Serial port
    if(!WriteFile(hComi, (void *)buffer, nbChar, &bytesSend, 0))
    {
        //In case it don't work get comm error and return false
        //ClearCommError(hCom, &this->errors, &this->status);

        return false;
    }
    else
        return true;
}

bool WriteData8(uint8_t *buffer, unsigned int nbChar,HANDLE	hComi)
{
    DWORD bytesSend;

    //Try to write the buffer on the Serial port
    if(!WriteFile(hComi, (void *)buffer, nbChar, &bytesSend, 0))
    {
        //In case it don't work get comm error and return false
        //ClearCommError(hCom, &this->errors, &this->status);

        return false;
    }
    else
        return true;
}
//////////////////////////////////////////////////////////////////////////

//Captures address and size of struct
void EasyTransfer::begin(uint8_t * ptr, uint8_t length)
{
    address = ptr;
    size = length;

    //dynamic creation of rx parsing buffer in RAM
    rx_buffer = (uint8_t*) malloc(size+1);
}

//Sends out struct in binary, with header, length info and checksum
void EasyTransfer::sendData(HANDLE	hComi)
{

    uint8_t CS = size;

    unsigned char bytestosend[2] = {0x06, 0x85};
    WriteData(bytestosend,2,hComi);
    WriteData8(&CS,1,hComi);

    for(int i = 0; i<size; i++)
    {
        CS^=*(address+i);
        WriteData8(address+i,1,hComi);

    }

    WriteData8(&CS,1,hComi);

}


bool EasyTransfer::receiveData(HANDLE	hComi)
{
     COMSTAT status;
    //Keep track of last error
    DWORD errors;
     ClearCommError(hComi, &errors, &status);

        //start off by looking for the header bytes. If they were already found in a previous call, skip it.
        if(rx_len == 0)
        {

            //this size check may be redundant due to the size check below, but for now I'll leave it the way it is.
            if(status.cbInQue >= 3){
            //this will block until a 0x06 is found or buffer size becomes less then 3.
                 while(ReadData(hComi) != 0x06) {
            	//This will trash any preamble junk in the serial buffer
            	//but we need to make sure there is enough in the buffer to process while we trash the rest
            	//if the buffer becomes too empty, we will escape and try again on the next call
            	if(status.cbInQue < 3)
            		return false;
            	}
                 if (ReadData(hComi) == 0x85)
                 rx_len = (uint8_t)ReadData(hComi);
            	//make sure the binary structs on both Arduinos are the same size.
                   if(rx_len != size){
                     rx_len = 0;
                     return false;
                   }
                 }
               }
            // }
            //we get here if we already found the header bytes, the struct size matched what we know, and now we are byte aligned.
             if(rx_len != 0){
               while(/*status.cbInQue && */rx_array_inx <= rx_len){
                 rx_buffer[rx_array_inx++] =(uint8_t)ReadData(hComi);
               }

               if(rx_len == (rx_array_inx-1)){
                 //seem to have got whole message
                 //last uint8_t is CS
                 calc_CS = rx_len;
                 for (int i = 0; i<rx_len; i++){
                   calc_CS^=rx_buffer[i];
                 }

                 if(calc_CS == rx_buffer[rx_array_inx-1]){//CS good
                   memcpy(address,rx_buffer,size);
            	rx_len = 0;
            	rx_array_inx = 0;
            	return true;
            	}

              else{
              //failed checksum, need to clear this out anyway
            	rx_len = 0;
            	rx_array_inx = 0;
            	return false;
              }

               }
             }
return false;
        }

Basically use it just like you would use the arduino one. Like i said ive just pulled the code direct so it will need a bit of work but you should be able to get it working. The only thing is ive as yet only used it with uint8_t. I cant be sure it will work for all data types. You can get round this by using a union though if you have to.
Also you will need to open a port, this is from my project and it's basically some code i found on the web, ive changed it slightly, it's the event for a connect button.

void testerFrame::OnconButClick(wxCommandEvent& event)  // CONNECT BOTTON
{

    if(!connection_flag)
    {


        wxString port = mesBox->GetValue();
        wxString baud = comSel->GetValue();
        char *portname;
        unsigned long baudrate;

        if(!baud.ToULong(&baudrate))
        {
            wxMessageBox(_("Enter a Valid BaudRate"), _("Warning"),wxICON_WARNING);
            return;
        }

        if(baudrate < 300 || baudrate > 460800  )
        {
            wxMessageBox(_("Enter a Valid BaudRate"), _("Warning"),wxICON_WARNING);
            return;
        }
        wxCharBuffer buffer=port.ToAscii();
        portname = ( buffer.data() );


        if(connectport(portname,baudrate))
        {
            wxMessageBox(_("Connected to port ")+port,_("Info"));
            conBut->SetLabel(_("Disconnect"));
            connection_flag = 1;
            ET.begin(details(mydata));
            ETin.begin(details(mydatain));

        }
        else
            wxMessageBox(port+_(" port not available"),_("Info"));
    }

    else
    {
        CloseHandle(hCom);
        connection_flag = 0;
        read_flag = 0;
        conBut->SetLabel(_("Connect"));
    }


}

I'm only learning as well so it might not be absolutely perfect!

Ah your on linux, sorry that was for windows

Hello kosh09,

under linux I do this to read and log all Serial.print from my arduinos

nohup script -a -f -c 'ttylog -b 9600 -d /dev/ttyACM0' /var/log/arduino.log &

In short,
nohup is to keep command active even after you log off of your linux,
script put in a log (/var/log/arduino.log) all the results of ttylog.
ttylog is reading everything on /dev/ACM0 (arduino) at -b speed
& is to daemonise the command script.

RTFM for the commands script and ttylog that you probably will have to install on your linux.

For instance you will have to change 9600 to watever you use.

Good luck.

EVP:
Ah your on linux, sorry that was for windows

It's ok :slight_smile: