Reading arduino serial in C++ using codeblocks on ubuntu - c++

I tried using and editing the code from Read and Write on serial port in Ubuntu with C/C++ and LibSerial and referencing from the Ubuntu manpage http://manpages.ubuntu.com/manpages/saucy/man3/LibSerial_SerialStream.3.html.
When I use the serial monitor from the Arduino IDE it works fine. But when I wanted to read it using codeblocks with C++, all I got was some garbage values.
Here's the code:
#include <SerialStream.h>
#include <iostream>
#include <stdlib.h>
#include <signal.h>
#include <unistd.h>
#define PORT "/dev/ttyUSB0"
using namespace std;
using namespace LibSerial;
...
SerialStreamBuf::BaudRateEnum baud_rate = SerialStreamBuf::BAUD_115200;
const SerialStreamBuf::CharSizeEnum csize = SerialStreamBuf::DEFAULT_CHAR_SIZE;
const SerialStreamBuf::ParityEnum parity = SerialStreamBuf::PARITY_NONE;
short stop_bits = 1;
const SerialStreamBuf::FlowControlEnum flow_c = SerialStreamBuf::FLOW_CONTROL_NONE;
...
SerialStream(PORT, baud_rate, csize, parity, stop_bits, flow_c);
SerialStream serial_port ;
serial_port.Open(PORT) ;
...
while( 1 ){
char next_byte;
serial_port.get(next_byte);
std::cerr << next_byte;
usleep(100);
}
How do I fix this? I'm not good in object oriented programming so I'm not so sure about initializing the constructors.

You're defining two variables for the serial stream, but using the uninitialized one. Try replacing this:
SerialStream(PORT, baud_rate, csize, parity, stop_bits, flow_c);
SerialStream serial_port ;
serial_port.Open(PORT) ;
With
SerialPort serial_port ;
serial_port.Open(PORT, baud_rate, csize, parity, stop_bits, flow_c);
and then use the ReadByte function.

Related

gcc compiler doesn't recognize my code for using Serial Port in Raspberry Pi 3

I'm compiling and running a C++/OpenCV program directly on the Raspberry Pi 3's Terminal with the line:
g++ pkg-config --cflags --libs opencv name.cpp -o name
I have been working like this without issues, but now I want to send some results like coordinates and numbers via serial port to Arduino, I tried to use this code:
#include <sstream>
#include <string>
#include <iostream>
#include <fstream>
#include <sys/time.h>
#include <termios.h>
#include <fcntl.h>
#include <sys/ioctl.h>
#include <sys/stat.h>
#include <sys/types.h>
#include <string.h>
#include <unistd.h>
#include <stdio.h>
//######################################################################
int fd = open("/dev/ttyAMS0", O_RDWR);
if (fd == -1) {
perror("/dev/ttyAMS0");
return 1;
}
struct termios tios;
tcgetattr(fd, &tios);
// disable flow control and all that, and ignore break and parity errors
tios.c_iflag = IGNBRK | IGNPAR;
tios.c_oflag = 0;
tios.c_lflag = 0;
cfsetspeed(&tios, B9600);
tcsetattr(fd, TCSAFLUSH, &tios);
// the serial port has a brief glitch once we turn it on which generates a
// start bit; sleep for 1ms to let it settle
usleep(1000);
// output to serial port
char msg[] = "hi there";
write(fd, msg, strlen(msg));
But now each time I try to compile I get the errors shown in the image Here:
So I guess I'm missing something, I have added all the libraries for the Serial Port as well but I don't know if I should add something on the line for compile as I did with the opencv libraries. Thanks in advance for your answers :)
I can't add comment so I will answer what I think about your problem.
Looks like your code written in global scope outer any function body.
You can't use if statement out of any function body.
Try to enclose your if statement in function body.
Something like this:
void chec(int fd) {
if (fd == -1) {
perror("/dev/ttyAMS0");
exit(1);
}
}
int fd = open("/dev/ttyAMS0", O_RDWR);
check(fd);

ACE c++ send_n and recv_n not working as expected

I am trying to implement a basic client-server program using ACE, but the problem is that if I send from client and receive it from server, it works properly. But, when I am increasing the complexity i.e., multiple sends and recvs the programs isn't working. Any help is appreciated.
Here's the client code.
#include "ace/SOCK_Acceptor.h"
#include "ace/SOCK_Connector.h"
#include "ace/SOCK_Stream.h"
#include "iostream"
using namespace std;
int main(){
ACE_INET_Addr server(7128);
ACE_SOCK_Connector cli;
ACE_SOCK_Stream cstream;
if(cli.connect(cstream, server)==-1){perror("Error");}
char buff[100];
if(-1==cstream.recv_n(buff, 7)){printf("Error");}
cout<<buff<<endl;
cstream.send_n("FU", 3);
}
Here's the server code
#include "ace/SOCK_Acceptor.h"
#include "ace/SOCK_Connector.h"
#include "ace/SOCK_Stream.h"
#include "iostream"
using namespace std;
int main(){
ACE_INET_Addr server(7128);
ACE_INET_Addr client;
ACE_SOCK_Acceptor cli(server);
ACE_SOCK_Stream cstream;
if(cli.accept(cstream, &client)==-1){perror("Error");}
char buff[100];
if(-1==cstream.send_n("RAND", 5)){printf("Error");}
cstream.recv_n(buff, 3);
}
Your server is sending 5 bytes but your client is expecting to read 7. The client is blocked waiting for 2 more bytes that will never come.

trouble with Open Cv and GPIO on mini6410

I am doing a simple project on arm based mini6410. I have debian package installed on mini. My project is to interface one IR motion sensor and I USB webcam with the mini6410. the working will be simple, whenever there will be any motion detected by IR sensor, the webcam will be on for 30 seconds save the images (over write the previous) and then off.
I have already cross comiled the Open CV code using arm-linux-gcc
For IR I am using GPE register.
Here I am stuck with a issue which I am unable to resolve. and even dont know how to resolve. OpenCv code is a cpp file camera.cpp and the file which deals with I/O ports is a C file named sensor.c. Now in that c file I am polling or whatever mechanism to check if the GPE register is 1 or not. If it is one, I should start the Open CV code which will start to capture images. further more this sensor.c file is not to be compiled rather made a module and then insmod on my mini6410.
However I dont know how to write c++ code in a c file. you can say i dont know how to call the OpenCV thing from the C file. as it is a module and within this i cant write the cpp code as then using namespace std and using namespace cv doesnot work.
i am new to embedded stuff and linux it self. so I wanted to know are there some possible solutions.
i am attaching my codes of both files.
This is sensor.c
#include <linux/module.h>
#include <linux/slab.h>
#include <linux/input.h>
#include <linux/init.h>
#include <linux/errno.h>
#include <linux/serio.h>
#include <linux/delay.h>
#include <linux/clk.h>
#include <linux/wait.h>
#include <linux/sched.h>
#include <linux/cdev.h>
#include <linux/miscdevice.h>
#include <asm/io.h>
#include <asm/irq.h>
#include <asm/uaccess.h>
#include <mach/map.h>
#include <mach/regs-clock.h>
#include <mach/regs-gpio.h>
#include <plat/gpio-cfg.h>
#include <mach/gpio-bank-q.h>
#include <mach/gpio-bank-e.h>
#include <mach/map.h>
#include <plat/regs-timer.h>
#include <mach/hardware.h>
#include <linux/kernel.h>
#include <linux/mm.h>
#include <linux/fs.h>
#include <linux/types.h>
#include <linux/moduleparam.h>
#include <linux/ioctl.h>
#include <linux/cdev.h>
#include <linux/string.h>
#include <linux/list.h>
#include <linux/pci.h>
#include <asm/uaccess.h>
#include <asm/atomic.h>
#include <asm/unistd.h>
#include <mach/gpio-bank-k.h>
#define RLV 0x0FFF
unsigned Gpe;
unsigned sensor_value;
typedef struct
{
int delay;
} TIM_DEV;
static TIM_DEV TimDev;
static irqreturn_t INTHandler(int irq,void *TimDev)
{
Gpe = readl(S3C64XX_GPEDAT);
Gpe &= ~(0xF<<1);
readl(sensor_value, S3C64XX_GPEDAT);
while (sensor_value == 1)
{//1 means that IR sensor has detected a motion and given a value of +5 V
for (i = 0; i < 30; i++){
//CV_function();
// delay here such that delay(1 s) * 30 = 30 seconds
}
}
return IRQ_HANDLED;
}
static struct file_operations dev_fops = {
.owner = THIS_MODULE,
.write = MyWrite,
};
static struct miscdevice misc = {
.minor = MISC_DYNAMIC_MINOR,
.name = DEVICE_NAME,
.fops = &dev_fops,
};
static int __init dev_init(void)
{
int ret;
unsigned TimerControl;
unsigned TimerINTControl;
unsigned TimerCNTB;
unsigned TimerCMPB;
unsigned TimerCFG1;
unsigned Ge;
TimerControl = readl(S3C_TCON);
TimerINTControl = readl(S3C_TINT_CSTAT);
TimerCNTB = readl(S3C_TCNTB(0));
TimerCMPB = readl(S3C_TCMPB(0));
TimerCFG1 = readl(S3C_TCFG1);
TimerCFG1 &= ~(S3C_TCFG1_MUX0_MASK);
TimerCNTB = RLV;
TimerCMPB = 0;
writel(TimerCNTB, S3C_TCNTB(0));
writel(TimerCMPB, S3C_TCMPB(0));
writel(TimerCFG1, S3C_TCFG1);
TimerControl |= S3C_TCON_T0MANUALUPD;
TimerINTControl |= S3C_TINT_CSTAT_T0INTEN;
writel(TimerControl, S3C_TCON);
writel(TimerINTControl, S3C_TINT_CSTAT);
TimerControl = readl(S3C_TCON);
TimerControl |= S3C_TCON_T0RELOAD;
TimerControl &= ~S3C_TCON_T0MANUALUPD;
TimerControl |= S3C_TCON_T0START;
writel(TimerControl, S3C_TCON);
//////////////Here I am configuring my GPE as input/////////////
Ge = readl(S3C64XX_GPECON);
Ge &= ~(0xFFFF<<4);
Ge |= (0x0000<<4);
writel(Ge, S3C64XX_GPECON);
/////////////
misc_register(&misc);
ret = request_irq(IRQ_TIMER0, INTHandler, IRQF_SHARED, DEVICE_NAME, &TimDev);
if (ret)
{
return ret;
}
return ret;
}
static void __exit dev_exit(void)
{
free_irq(IRQ_TIMER0, &TimDev);
misc_deregister(&misc);
}
module_init(dev_init);
module_exit(dev_exit);
MODULE_LICENSE("GPL");
MODULE_AUTHOR("XYZ");
this is camera.cpp
#include <opencv2/objdetect/objdetect.hpp>
#include <opencv2/highgui/highgui.hpp>
#include <opencv2/imgproc/imgproc.hpp>
#include <iostream>
#include <stdio.h>
using namespace std;
using namespace cv;
int main( int argc, const char** argv )
{CvCapture* capture = 0;
Mat frame, frameCopy, image;
capture = cvCaptureFromCAM( 2 );
if( !capture )
{
cout << "No camera detected" << endl;
}
if( capture )
{
cout << "In capture ..." << endl;
IplImage* iplImg = cvQueryFrame( capture );
frame = iplImg;
if( frame.empty() )
break;
if( iplImg->origin == IPL_ORIGIN_TL )
frame.copyTo( frameCopy );
else
flip( frame, frameCopy, 0 );
cvSaveImage("image.jpg" ,iplImg);
}
cvReleaseCapture( &capture );
return 0;
}
the for loop in the sensor.c file should have my this above code by some means
I hope you get the idea,
Thanks
The missing link in the code shown is a mechanism by which the user-space code shown above can get notification of a change in the GPIO pin detected by the device driver.
There are two obvious ways to achieve this:
Integrate the GPIO pin into the platform's GPIO resources and then use the generic sysfs mechanism from user-space. The Linux kernel GPIO documentation describes both kernel and user-space side of this.
Have your driver expose a sysfs node for the GPIO line. sysfs is fundamental to the Linux Driver Model. I suggest a thorough read of Linux Device Drivers 3rd Edition.
The user-space side of either method is similar: You open the sysfs resource exported by your module and then use either poll() or select() to block until an event occurs.

Redirection in Linux with dup2() and create() inside a loop

I am running the code below and I cannot redirect to a file. The file is made, but nothing is put into it. If I remove the last dup2(saveout,1) statement, I can create and write into the file, but I cannot get back to the terminal, which is important. As soon as I put the dup2(saveout,1) back in my code, the redirection stops working, but I can get back to the terminal. I do not understand why this is happening. I would like to redirect and go back into the terminal.
main.cpp
#include <cstdlib>
#include <stdio.h>
#include <stdlib.h>
#include <fcntl.h>
#include <string>
#include <iostream>
#include <string.h>
#include <unistd.h>
#include <sys/stat.h>
using namespace std;
void printmessage() {
printf("this is the message\n");
}
int main(int argc, char** argv) {
int saveout;
int fd;
saveout = dup(1);
for (int i = 0; i < 10; i++) {
fd = creat("/home/carl/example.txt",O_CREAT|O_APPEND);
dup2(fd, 1);
close(fd);
printf("Testing the message");
printmessage();
dup2(saveout,1);
close(saveout);
}
return 0;
}
This is a file rights issue, you should read the man pages of the functions you are using.
creat() takes as first argument the filename, and as second the file creation rights, not its opening mode.
The creat() functions is a simple open() call, with some particular flags, so that you'll just have to set up the rights.
if you want to open your file, and create it if he doesn't exists, use
open(filename, O_CREAT | O_RDWR | O_APPEND, 0600) for example, or
creat(filename, 0600),
which is mostly its equivalent, but you wont be able to append text, as "creat() is equivalent to open() with flags equal to O_CREAT | O_WRONLY | O_TRUNC"
The second dup2(saveout,1); will fail because you closed saveout.
printf is buffered by default. (line-by-line for output to a tty, perhaps differently for output to something else). Before both your calls to dup2(..., 1), you should flush with fflush:
fflush(stdout);

reading linux inode bitmap

I'm going to fetch linux inode bitmaps with c++. I've use this code to fetch super block first:
#include <cstdlib>
#include <linux/ext2_fs.h>
#include <linux/fs.h>
#include <iostream>
#include <stdio.h>
#include <fstream>
#include <fcntl.h>
#include <linux/fs.h>
using namespace std;
/*
*
*/
int main() {
int fd;
char boot[1024];
struct ext2_super_block super_block;
fd = open("/dev/sda1", O_RDONLY);
/* Reads the boot section and the superblock */
read(fd, boot, 1024);
read(fd, &super_block, sizeof (struct ext2_super_block));
/* Prints the Magic Number */
printf("%x\n", super_block.s_magic);
close(fd);
return 0;
}
but every time i run it , i get a error :
In file included from main.cpp:2:0:
/usr/include/linux/ext2_fs.h:181:18: error: ‘S_ISDIR’ was not declared in this scope
/usr/include/linux/ext2_fs.h:183:23: error: ‘S_ISREG’ was not declared in this scope
I couldn't find any good example or tutorial for this.is there anybody to help me?
EDIT :
I've include <linux/stat.h> but still get same error.
#grep -rw S_ISREG /usr/src/linux/include
/usr/src/linux/include/linux/fs.h: if (S_ISREG(inode->i_mode) || S_ISDIR(inode->i_mode) ||
/usr/src/linux/include/linux/fs.h.~1~: if (S_ISREG(inode->i_mode) || S_ISDIR(inode->i_mode) ||
/usr/src/linux/include/linux/stat.h:#define S_ISREG(m) (((m) & S_IFMT) == S_IFREG)
So you should find stat.h in yours kernel source tree and include it.
The Linux source code "stat.h" is not the same file as that comes with the C-library. They just happen to have the same name. You will need to set your include path to find the correct stat.h (you may need BOTH, depending on what you are trying to do).