# How to read the laserscan,store and display it simultaneously (Topics\_quiz)

**URL:** <https://get-help.theconstruct.ai/t/how-to-read-the-laserscan-store-and-display-it-simultaneously-topics-quiz/990>\
**Category:** ROS Basics In 5 Days (C++)\
**Created:** [October 9, 2019, 9:27pm UTC](https://get-help.theconstruct.ai/t/how-to-read-the-laserscan-store-and-display-it-simultaneously-topics-quiz/990 "2019-10-09T21:27:28Z")\
**Posts on this page:** 9\
**Page:** 1

<div class="post-metadata">

**Author:** ![adityasrichandan3098](https://get-help.theconstruct.ai/user_avatar/get-help.theconstruct.ai/adityasrichandan3098/32/10_2.png) [@adityasrichandan3098](https://get-help.theconstruct.ai/u/adityasrichandan3098)\
**Post date:** [October 9, 2019, 9:27pm UTC](https://get-help.theconstruct.ai/t/how-to-read-the-laserscan-store-and-display-it-simultaneously-topics-quiz/990/1 "2019-10-09T21:27:28Z")

</div>

I have written a Piece of code to subscribe /Kobuki/laser/scan and publish some twist message to bot and ahead is a wall(obstacle) , I want to get laser data while bot is moving.  
But I am getting a ‘Segmentation fault (core dumped)’. Why is it so?

Code:

#include\<ros/ros.h\>  
#include\<sensor\_msgs/LaserScan.h\>  
#include\<geometry\_msgs/Twist.h\>

ros::Publisher pub;  
ros::Subscriber sub;

sensor\_msgs::LaserScan lsvalue;  
geometry\_msgs::Twist vel;

void laser\_callback(const sensor\_msgs::LaserScan::ConstPtr& msg){  
int range=msg-\>ranges.size();  
for(int i=0;i\<range;i++){  
lsvalue.ranges[i]=msg-\>ranges[i]+1;

```
}

```

}  
int main(int argc,char\*\* argv){  
ros::init(argc, argv, “topics\_quiz\_node”);  
ros::NodeHandle nh;  
pub=nh.advertise\<geometry\_msgs::Twist\>("/cmd\_vel", 1000);  
sub=nh.subscribe("/kobuki/laser/scan",1000, laser\_callback);  
ros::Rate loop(1);  
for( int i=0; i\<5;i++){  
vel.linear.x=0.2;  
pub.publish(vel);  
}  
vel.linear.x=0;  
pub.publish(vel);  
while(ros::ok()){  
for (int i=0;i\<lsvalue.ranges.size();i++){  
ROS\_INFO(“Data %f”, lsvalue.ranges[i]);  
loop.sleep();  
}  
ros::spinOnce();  
loop.sleep();  
}

```
return 0;

```

}

---

<div class="post-metadata">

**Author:** ![simon.steinmann91](https://get-help.theconstruct.ai/user_avatar/get-help.theconstruct.ai/simon.steinmann91/32/324_2.png) [@simon.steinmann91](https://get-help.theconstruct.ai/u/simon.steinmann91)\
**Post date:** [October 9, 2019, 9:59pm UTC](https://get-help.theconstruct.ai/t/how-to-read-the-laserscan-store-and-display-it-simultaneously-topics-quiz/990/2 "2019-10-09T21:59:20Z")

</div>

Hi @adityasrichandan3098,  
please post the whole error message

---

<div class="post-metadata">

**Author:** ![adityasrichandan3098](https://get-help.theconstruct.ai/user_avatar/get-help.theconstruct.ai/adityasrichandan3098/32/10_2.png) [@adityasrichandan3098](https://get-help.theconstruct.ai/u/adityasrichandan3098)\
**Post date:** [October 10, 2019, 10:34am UTC](https://get-help.theconstruct.ai/t/how-to-read-the-laserscan-store-and-display-it-simultaneously-topics-quiz/990/3 "2019-10-10T10:34:11Z")

</div>

![image](https://get-help.robotigniteacademy.com/uploads/default/original/1X/71f82b4121a38d7c0313f86d56f2069d082fb914.png)

---

<div class="post-metadata">

**Author:** ![adityasrichandan3098](https://get-help.theconstruct.ai/user_avatar/get-help.theconstruct.ai/adityasrichandan3098/32/10_2.png) [@adityasrichandan3098](https://get-help.theconstruct.ai/u/adityasrichandan3098)\
**Post date:** [October 10, 2019, 2:43pm UTC](https://get-help.theconstruct.ai/t/how-to-read-the-laserscan-store-and-display-it-simultaneously-topics-quiz/990/4 "2019-10-10T14:43:51Z")

</div>

![image](https://get-help.robotigniteacademy.com/uploads/default/original/1X/a4166aa3f706f4a1f3eb1e3f4d5a2d7339ba4919.png)

I have added a code to check if i am getting the laser call back, it seems my laser.ranges seems to be empty. i.e I am not receiving the laserscan data. How do I wait for the data? My program if exiting once executed with segmentation fault due to empty range.

float laser(sensor\_msgs::LaserScan& Laser){  
if(!(Laser.ranges.empty())){  
return Laser.ranges[(Laser.ranges.size())/2];  
}  
else{  
ROS\_INFO(“waiting”);  
return 0;  
}  
}

---

<div class="post-metadata">

**Author:** ![simon.steinmann91](https://get-help.theconstruct.ai/user_avatar/get-help.theconstruct.ai/simon.steinmann91/32/324_2.png) [@simon.steinmann91](https://get-help.theconstruct.ai/u/simon.steinmann91)\
**Post date:** [October 10, 2019, 4:00pm UTC](https://get-help.theconstruct.ai/t/how-to-read-the-laserscan-store-and-display-it-simultaneously-topics-quiz/990/5 "2019-10-10T16:00:30Z")

</div>

Thanks for the clarification.  
This is a perfect exercise for troubleshooting. I’m not too familiar with c++, but here are 2 links that might help:  
[https://www.cprogramming.com/debugging/segfaults.html](https://www.cprogramming.com/debugging/segfaults.html)  
[https://jvns.ca/blog/2018/04/28/debugging-a-segfault-on-linux/](https://jvns.ca/blog/2018/04/28/debugging-a-segfault-on-linux/)

How I would troubleshoot this:

1. remove your whole if-then-else part of the functions and see if that is what causes the error
2. add ROS\_INFO() on different steps of the way, to print info you need. For example you can print  
ROS\_INFO(Laser.ranges.size()) before your check, in the if and in the else loop. See what your program does. Perhaps a command or syntax you use, does something different to what you think
3. check the core dump (perhaps do this first)

---

<div class="post-metadata">

**Author:** ![bayodesegun](https://get-help.theconstruct.ai/user_avatar/get-help.theconstruct.ai/bayodesegun/32/10684_2.png) [@bayodesegun](https://get-help.theconstruct.ai/u/bayodesegun)\
**Post date:** [October 10, 2019, 7:12pm UTC](https://get-help.theconstruct.ai/t/how-to-read-the-laserscan-store-and-display-it-simultaneously-topics-quiz/990/6 "2019-10-10T19:12:44Z")

</div>

Hi @adityasrichandan3098,

Looking at your code, I can see the following:

- You are trying to put your LaserScan message into `lsvalue`, but it seems it’s not being done rightly. But…you don’t even need to do that! In your `laser_callback`, just print the messages you are printing in `main()` by accessing `msg` directly.

- Your are missing `ros::spin()` in `main()`, so your subscriber is not working properly (`spinOnce()` is not enough for this case, as you need to keep subscribing to the laser scan. See the difference between `spin()` and `spinOnce()` in the post below:  
[What is rospy.spin(), ros::spin(), ros::spinOnce(), and what are they for?](https://get-help.robotigniteacademy.com/t/what-is-rospy-spin-ros-spin-ros-spinonce-and-what-are-they-for/58)

- Don’t stop the robot in `main()`, like you’re doing here:

```auto
vel.linear.x=0;
pub.publish(vel);

```

- You don’t need the `Rate` object here:  
[Proper use of rospy.Rate or ros::Rate](https://get-help.robotigniteacademy.com/t/proper-use-of-rospy-rate-or-ros-rate/59)

- You don’t need to do any publishing in the `main` function - do them in the `laser_callback`, based on the sensor reading. If you must do any publication in `main()`, let it be the initial one and then do the rest in the callback. Your main should be something like:

```auto
int main(int argc,char** argv){
   ros::init(argc, argv, “topics_quiz_node”);
   ros::NodeHandle nh;
   pub=nh.advertise<geometry_msgs::Twist>("/cmd_vel", 1000);
   sub=nh.subscribe("/kobuki/laser/scan",1000, laser_callback);
   // Do just the initial publication here; do the rest in the callback
   // Not really necessary though
   for(int i=0; i<5;i++){
     vel.linear.x=0.2;
     pub.publish(vel);
   }
   // This is necessary for the LaserScan message to keep arriving 
   // and for the program to keep running
   ros::spin();
}

```

Your `laser_callback()` could be something like:

```auto
void laser_callback(const sensor_msgs::LaserScan::ConstPtr& msg){
  // print your ranges array for debugging.
  // the middle values represent the front-center of the robot
  // the first and last represent the extreme sides
  if (/*robot is not too close for comfort*/) {
    vel.linear.x = 0.2; // move forward
    vel.anguar.z = 0; // no turning for now
  }
  else {
    vel.angular.z = -0.2 // or 0.2, turn
    vel.angular.x = 0; // no forward movement for now
  }
  pub.publish(vel);
}

```

---

<div class="post-metadata">

**Author:** ![adityasrichandan3098](https://get-help.theconstruct.ai/user_avatar/get-help.theconstruct.ai/adityasrichandan3098/32/10_2.png) [@adityasrichandan3098](https://get-help.theconstruct.ai/u/adityasrichandan3098)\
**Post date:** [October 11, 2019, 6:43am UTC](https://get-help.theconstruct.ai/t/how-to-read-the-laserscan-store-and-display-it-simultaneously-topics-quiz/990/7 "2019-10-11T06:43:16Z")

</div>

Yup! thanks @bayodesegun Now I have a good Idea on how to use ros::spin, ros::spinOnce and ros::rate.

Yet my sensor message seems to get lost somewhere! I have written the code again, and yet again I am not able to receive the laser scan data.

```
 #include<ros/ros.h>
 #include<sensor_msgs/LaserScan.h>
 #include<geometry_msgs/Twist.h>

class AvoidWall{
private:
    ros::NodeHandle _n;
    ros::Publisher _pub;
    ros::Subscriber _sub;
    geometry_msgs::Twist _vel;
    sensor_msgs::LaserScan _lsval;

public:

    AvoidWall(){
        _pub=_n.advertise<geometry_msgs::Twist>("/cmd_vel", 1000);
        _sub=_n.subscribe("/kobuki/Laser/scan",1000,&AvoidWall::laser_callback,this);

    }
    void move(){
        ros::Rate rate(20);
        for(int i=0;i<10;i++){
            _vel.linear.x=0.5;
            _pub.publish(_vel);
            rate.sleep();
            ROS_INFO("MOVING");
        }
        _vel.linear.x=0;
        _pub.publish(_vel);
        ROS_INFO("DONE!");
    }
    void laser_callback(const sensor_msgs::LaserScan::ConstPtr& msg){

        for(int i=0;i<(msg->ranges.size());i++){
            //_lsval.ranges[i]=msg->ranges[i];
            if(!(msg->ranges.empty()))
            ROS_INFO("data %f",msg->ranges[i]);
            else{
                ROS_INFO("NO VALUE");
            }
        }
    }
};
int main(int argc, char** argv)
{
         ros::init(argc, argv,"topics_quiz_node");
         AvoidWall obj;

obj.move();

ros::spin();
return 0;

```

}

 ![image](https://get-help.robotigniteacademy.com/uploads/default/original/1X/a883567306e6f09c4befb43908299cc8c0713343.png)

After “MOVING” is displayed, I am not getting the callback function called.

---

<div class="post-metadata">

**Author:** ![simon.steinmann91](https://get-help.theconstruct.ai/user_avatar/get-help.theconstruct.ai/simon.steinmann91/32/324_2.png) [@simon.steinmann91](https://get-help.theconstruct.ai/u/simon.steinmann91)\
**Post date:** [October 11, 2019, 3:29pm UTC](https://get-help.theconstruct.ai/t/how-to-read-the-laserscan-store-and-display-it-simultaneously-topics-quiz/990/8 "2019-10-11T15:29:23Z")

</div>

I’m not good with c++. but try to remove the obj.move() , just have

```auto
AvoidWall obj;
ros::spin();

```

call the move function from within your callback.

---

<div class="post-metadata">

**Author:** ![adityasrichandan3098](https://get-help.theconstruct.ai/user_avatar/get-help.theconstruct.ai/adityasrichandan3098/32/10_2.png) [@adityasrichandan3098](https://get-help.theconstruct.ai/u/adityasrichandan3098)\
**Post date:** [October 11, 2019, 5:44pm UTC](https://get-help.theconstruct.ai/t/how-to-read-the-laserscan-store-and-display-it-simultaneously-topics-quiz/990/9 "2019-10-11T17:44:17Z")

</div>

Thanks! for mentioning @simon.steinmann91 @bayodesegun, btw I found the problem,I mispelled  
/kobuki/laser/scan topic.
