Error: (E109) complete binding failed: port not bound - systemc

I am trying to design an LFSR counter in SystemC which should look something like this: (click to see picture)
I think there is something wrong with connections between modules shiftreg.h and lfsr-feedback.h in the lfsr.h file, but I can't figure out what the problem is.
I get this error message while running on terminal:
Error: (E109) complete binding failed: port not bound: port 'top_p.LFSR_p.shiftReg_p.port_3' (sc_in)
In file: ../../../../src/sysc/communication/sc_port.cpp:231
This is how the main.cpp file looks like:
#include <iostream>
#include "systemc.h"
#include "lfsr.h"
#include "stim_shiftReg.h"
SC_MODULE(TOP)
{
LFSR *LFSR_p;
stim_shiftReg *stim_shiftReg_p;
sc_clock sig_clk; //define clock pin
sc_signal< bool > sig_rst;
sc_signal< bool > sig_lshift;
sc_signal< sc_bv<8> > sig_out;
SC_CTOR(TOP) : sig_clk ("ClockSignal", 20, SC_NS)
{
stim_shiftReg_p = new stim_shiftReg("stim_shiftReg_p");
stim_shiftReg_p -> clk(sig_clk); //input bool
stim_shiftReg_p -> rst(sig_rst); //input bool
stim_shiftReg_p -> stim_lshift(sig_lshift); //input bool
stim_shiftReg_p -> stim_out(sig_out); //output sc_bv
LFSR_p = new LFSR("LFSR_p");
LFSR_p -> clk(sig_clk); //input bool
LFSR_p -> rst(sig_rst); //input bool
LFSR_p -> lshift(sig_lshift);
LFSR_p -> out(sig_out); //output sc_bv
}
~TOP(){
//free up memory
delete LFSR_p;
delete stim_shiftReg_p;
}
};
TOP *top_p = NULL;
int sc_main(int argc, char* argv[])
{
sc_set_time_resolution(1, SC_NS);
top_p = new TOP("top_p");
sc_start();
return 0;
}
This is how lfsr.h file looks like:
#include"systemc.h"
#include"shiftReg.h"
#include"lfsr_feedback.h"
SC_MODULE(LFSR)
{
shiftReg *shiftReg_p;
lfsr_feedback *lfsr_feedback_p;
//define input
sc_in<bool> clk;
sc_in<bool> rst;
sc_in<bool> lshift;
//define output
sc_out<sc_bv<8> > out;
sc_signal<bool> rightin;
SC_CTOR(LFSR)
{
shiftReg_p = new shiftReg("shiftReg_p");
shiftReg_p -> clk(clk); //input bool
shiftReg_p -> rst(rst); //input bool
shiftReg_p -> lshift(lshift); //enable shift signal connection
shiftReg_p -> out(out); //output sc_bv
lfsr_feedback_p = new lfsr_feedback("lfsr_feedback_p");
lfsr_feedback_p -> clk(clk); //input bool
lfsr_feedback_p -> rst(rst); //input bool
lfsr_feedback_p -> rightin(rightin); //feedback signal
lfsr_feedback_p -> out(out); //output sc_bv
}
~LFSR()
{
//free up memory
delete shiftReg_p;
delete lfsr_feedback_p;
}
};
This is shiftReg.h:
#include<iostream>
#include<systemc.h>
SC_MODULE(shiftReg) //'shiftReg' - Module name
{
//define input
sc_in<bool> clk;
sc_in<bool> rst;
sc_in<bool> lshift;
sc_in<bool> rightin;
//define output
sc_out<sc_bv<8> > out;
sc_bv<8> RegValue;
SC_CTOR(shiftReg) //'shiftReg' - Module name
{
SC_CTHREAD(ShiftReg, clk.pos());
async_reset_signal_is(rst, true);
}
private:
void ShiftReg()
{
//Reset actions
RegValue = (11111111); //Use RegValue to store the register value
wait();
std::cout << "Reset done! RegisterValue = " << RegValue << endl;
wait();
while(true)
{
if(lshift.read() == true)
{
RegValue = RegValue << 1; //shift to the left
RegValue[0] = rightin.read();
std::cout << "Left shift done! RegisterValue = " << RegValue << endl;
}
else //if both are set to FALSE, no action should happen
{
std::cout << "'lshift' is set to FALSE status. No shift is done!" << endl;
}
out.write(RegValue); //Write output value to the out port
wait();
}
};
};
And this is lfsr_feedback.h:
#include<iostream>
#include<systemc.h>
SC_MODULE(lfsr_feedback) //'lfsr_feedback' - Module name
{
sc_in< bool > clk;
sc_in< bool > rst;
sc_out< bool > rightin;
sc_in< sc_bv<8> > out;
sc_signal<bool> fb_xor, a, b, c, d;
SC_CTOR(lfsr_feedback) //'lfsr_feedback' - Module name
{
SC_CTHREAD(Feedaback_Gen, clk.pos());
async_reset_signal_is(rst, true);
}
private: void Feedaback_Gen()
{
wait();
while(true)
{
a = out[7]; b = out[5]; c = out[4]; d = out[3];
std::cout << "Load random bits" << endl;
fb_xor = (a ^ b) ^ (c ^ d);
std::cout << "Calculate xor value!" << rightin << endl;
rightin.write(fb_xor);
wait();
}
};
};
And this is stim_shiftReg.h:
#include "systemc.h"
SC_MODULE(stim_shiftReg)
{
//define stimuli input for shift register
sc_in<bool> clk;
sc_out<bool> rst;
sc_out<bool> stim_lshift;
//define stimuli output for shift register
sc_in<sc_bv<8> > stim_out;
SC_CTOR(stim_shiftReg) { //'stim_shiftReg' module name
SC_CTHREAD(Stim_Shift, clk.pos());
}
private:
void Stim_Shift() {
//Simulate reset signal
wait();
rst.write(true);
wait();
rst.write(false);
//Write input value for 'in'
stim_lshift.write(true); //enable shifting
wait(40000);
sc_stop();
};
};
Note: I am not sure about port out which is in lfsr.h. It is an sc_out<T> from shiftReg.h and also as an output form LFSR.h. But, the same port should be an input to lfsr_feedback.h.

The port "lshift" is not bound in TOP module.
See my comment inline:
#include <iostream>
#include "systemc.h"
#include "lfsr.h"
#include "stim_shiftReg.h"
SC_MODULE(TOP)
{
LFSR *LFSR_p;
stim_shiftReg *stim_shiftReg_p;
sc_clock sig_clk; //define clock pin
sc_signal< bool > sig_rst;
sc_signal< bool > sig_lshift;
sc_signal< sc_bv<8> > sig_out;
SC_CTOR(TOP) : sig_clk ("ClockSignal", 20, SC_NS)
{
stim_shiftReg_p = new stim_shiftReg("stim_shiftReg_p");
stim_shiftReg_p -> clk(sig_clk); //input bool
stim_shiftReg_p -> rst(sig_rst); //input bool
stim_shiftReg_p -> stim_lshift(sig_lshift); //input bool
stim_shiftReg_p -> stim_out(sig_out); //output sc_bv
LFSR_p = new LFSR("LFSR_p");
LFSR_p -> clk(sig_clk); //input bool
LFSR_p -> rst(sig_rst); //input bool
LFSR_p -> out(sig_out); //output sc_bv
LFSR_p -> lshift(sig_lshift); //< The missing lshift port bind.
}
~TOP(){
//free up memory
delete LFSR_p;
delete stim_shiftReg_p;
}
};
TOP *top_p = NULL;
int sc_main(int argc, char* argv[])
{
sc_set_time_resolution(1, SC_NS);
top_p = new TOP("top_p");
sc_start();
return 0;
}
Update: You can still use the initializer list method to call constructors for SystemC objects.
From you code sample:
SC_MODULE(LFSR)
{
shiftReg *shiftReg_p;
lfsr_feedback *lfsr_feedback_p;
//define input
sc_in<bool> clk;
sc_in<bool> rst;
sc_in<bool> lshift;
//define output
sc_out<sc_bv<8> > out;
sc_signal<bool> rightin;
SC_CTOR(LFSR):
clk("clk") //<< Added these lines
, rst("rst") //<< Added these lines
, lshift("lshift") //<< Added these lines
, out("out") //<< Added these lines
, rightin("rightin") //<< Added these lines
{
These changes would make the error messages more meaningful rather than just printing port_3 is not bound.
Update 2:
The port in "rightin" in module is not bound in the module: LFSR (In lfsr.h)
SC_CTOR(LFSR)
{
shiftReg_p = new shiftReg("shiftReg_p");
shiftReg_p -> clk(clk); //input bool
shiftReg_p -> rst(rst); //input bool
shiftReg_p -> lshift(lshift); //enable shift signal connection
shiftReg_p -> out(out); //output sc_bv
shiftReg_p -> rightin(rightin); //< Missing statement.
lfsr_feedback_p = new lfsr_feedback("lfsr_feedback_p");
lfsr_feedback_p -> clk(clk); //input bool
lfsr_feedback_p -> rst(rst); //input bool
lfsr_feedback_p -> rightin(rightin); //feedback signal
lfsr_feedback_p -> out(out); //output sc_bv
}
Note: Kindly follow the changes mentioned in the previous update so as to get more meaningful error messages than just getting "port_3" is not bound.

1) Most likely you forgot to bind port "out" of LFSR module instance
2) You should always initialize all sc_objects with names, so you can get readable errors. For example in C++11 you can initialize members in-place
//define input
sc_in<bool> clk{"clk"};
sc_in<bool> rst{"rst"};
sc_in<bool> lshift{"lshift"};
//define output
sc_out<sc_bv<8> > out{"out"};

One way to deal with the less than useful message:
Error: (E109) complete binding failed: port not bound: port 'top_p.LFSR_p.shiftReg_p.port_3' (sc_in)
is to use egrep on the header file that is defining the ports of the module (guessing here):
egrep "sc_in|sc_out" shiftReg_p.h
Then you will see a list of the sc_in and sc_out in numeric order, and then have a clue which one is port_3.

Related

Member of b object can't write in SystemC

I got this error on SystemC, and I don't understand why. The error is:
'write': is not a member of
'sc_core::sc_in' ConsoleApplication1
'write': is not a member of 'sc_core::sc_in'
class "sc_core::sc_in" has no member "write"
class "sc_core::sc_in" has no member "write"
Here I put together the code.
#include<systemc.h>
SC_MODULE(prin) {
sc_in<bool> a;
void print() {
cout << "Hello World\n";
}
SC_CTOR(prin) {
SC_METHOD(print);
sensitive << a;
}
};
SC_MODULE(input) {
prin b;
void in() {
b.a.write(false);
wait();
b.a.write(true);
wait();
}
SC_CTOR(input) : b("sds"){
SC_THREAD(in);
}
};
int sc_main(int argc, char* argv[]) {
input prin1("pint");
sc_start();
return 0;
}
If the error seems confusing, here I put together the picture of my error:
The port "a" is an input port so cannot be written to. If you make it an output port then you can write to it. Also, the port is not bound so you will also get an error for that so I have bound a signal to it just so it compiles.
#include <systemc.h>
SC_MODULE(prin) {
sc_out<bool> a; //output port
sc_signal<bool> sig; //something to bind port a to
void print() {
cout << "Hello World\n";
}
SC_CTOR(prin) {
SC_METHOD(print);
sensitive << a;
a(sig); //bind port a to s signal
}
};
SC_MODULE(input) {
prin b;
void in() {
b.a.write(false);
wait();
b.a.write(true);
wait();
}
SC_CTOR(input) : b("sds"){
SC_THREAD(in);
}
};
int sc_main(int argc, char* argv[]) {
input prin1("pint");
sc_start();
return 0;
}
Then
g++ -file.cpp -lsystemc
./a.out
Gives me the output
SystemC 2.3.2-Accellera --- Apr 16 2018 00:15:03
Copyright (c) 1996-2017 by all Contributors,
ALL RIGHTS RESERVED
Hello World

Port not bound SystemC (E112)

I am trying to implement a producer (master) speaking to a memory element (slave) through the memory controller (which implements the interface simple_mem_interface).
Note: Some functions details and include statements are not fully mentioned in the code attached.
Searching for bugs in the code.
Adding debugging tools to find the fault in Write Enable Port.
binding.cpp
int sc_main(int argc, char* argv[])
{
sc_signal<unsigned int> d_out,d_in,address_d;
sc_signal<bool> wen, ren, ack;
sc_clock ClkFast("ClkFast", 100, SC_NS);
sc_clock ClkSlow("ClkSlow", 50, SC_NS);
Memory_Controller Controller1 ("Controller");
d_out = Controller1.data_mem_read;
ren.write(Controller1.REN);
ack.write(Controller1.ack);
d_in.write(Controller1.data_write);
address_d.write(Controller1.address);
wen.write(Controller1.WEN);
producer P1("Producer");
P1.out(Controller1);
P1.Clk(ClkFast);
Memory_module MEM("Memory");
MEM.Wen(wen);
MEM.Ren(ren);
MEM.ack(ack);
MEM.Clock(ClkSlow);
MEM.data_in(d_in);
MEM.data_out(d_out);
MEM.address(address_d);
sc_start(5000, SC_NS);
return 0;
Memory_controller.h
#define MEM_SIZE 100
#include <interface_func.h>
class Memory_Controller : public sc_module, public simple_mem_if
{
public:
// Ports
sc_in <unsigned int> data_mem_read{ "Data_Read_from_Memory" };
sc_out<bool> REN { "Read_Enable" };
sc_out<bool> WEN { "Write_Enable" };
sc_out <bool> ack{ "ACK_Bool" };
sc_out<unsigned int> address{ "Memory_Address" }, data_write{
"Data_Written_to_Memory" };
// constructor
Memory_Controller(sc_module_name nm) : sc_module(nm)
{ // Creating a 2 dimentional array holding adresses and data
WEN.write(false);
REN.write(false);
ack.write(false);
}
~Memory_Controller() //destructor
{
}
bool Write(unsigned int address_i, unsigned int datum) // blocking write
{
WEN.write(true);
REN.write(false);
data_write.write(datum);
address.write(address_i);
if (ack == true)
return true;
else
return false;
}
bool Read(unsigned int address_i, unsigned int& datum_i) // blocking read
{
WEN.write(false);
REN.write(true);
datum_i=data_mem_read;
address.write(address_i);
if (ack == true)
return true;
else
return false;
}
void register_port(sc_port_base& port, const char* if_typename)
{
cout << "binding " << port.name() << " to "
<< "interface: " << if_typename << endl;
}
};
Memory.h
#define MEM_SIZE 100
#include "interface_func.h"
class Memory_module : public sc_module
{
public:
sc_in<bool> Wen,Ren;
sc_in <unsigned int> address, data_in ;
sc_in<bool> Clock;
sc_out <unsigned int> data_out;
sc_out <bool> ack;
bool fileinput = false;
ifstream myfile;
unsigned int item [MEM_SIZE];
Memory_module()
{
}
void Write() // blocking write
{
while (true)
{
wait();
if (Wen==true)
{
if (address >= MEM_SIZE || address < 0)
{
ack=false;
}
else
{
item[address]=data_in;
ack=true;
}
}
}
}
void Read() // blocking read
{
while (true)
{
wait();
if (Ren)
{
if (address >= MEM_SIZE || address < 0)
ack=false;
else
{
data_out.write(item[address]);
ack=true;
}
}
}
}
SC_CTOR(Memory_module)
{
SC_THREAD(Read);
sensitive << Clock.pos();
SC_THREAD(Write);
sensitive << Clock.pos();
}
};
interface_func.h
class simple_mem_if : virtual public sc_interface
{
public:
virtual bool Write(unsigned int addr, unsigned int data) = 0;
virtual bool Read(unsigned int addr, unsigned int& data) = 0;
};
After debugging the SystemC binder.cpp code, the following error arises:
(E112) get interface failed: port is not bound : port 'Controller.Write_Enable' (sc_out)
You cannot drive your unconnected ports in the Memory_Controller constructor. If you want to explicitly drive these ports during startup, move these calls to a start_of_simulation callback:
Memory_Controller(sc_module_name nm) : sc_module(nm)
{}
void start_of_simulation()
{
WEN.write(false);
REN.write(false);
ack.write(false);
}

Changing signal on every posedge of clock in SC_THREAD

I want to implement module, which when is called to work changes signal x the way below:
1 clk pos.edge : x = 0 // 1st phase
2 clk pos.edge : x = 0 // 2nd phase
3 clk pos.edge : x = 1 // 3rd phase
And then stops until called again.
I have function foo() in my module, which is called from main and allows thread work_foo() to execute on the posedge of clock.
I tried to do it this way (with wait()), and in some simple test it gives right wave, but it is an inappropriate way: my_module.h:
#include "systemc.h"
SC_MODULE (my_module)
{
sc_in <bool> clk;
sc_out <sc_logic> x;
sc_signal <bool> valid;
void foo()
{
valid = 1;
return;
}
void work_foo()
{
while (true)
{
if (valid == 1)
{ // foo() was called
if (phase == 0)
{
x = SC_LOGIC_0;
wait(); // waiting for the next tick
x = SC_LOGIC_0;
wait(); // waiting for the next tick
x = SC_LOGIC_1;
wait(); // waiting for the next tick
}
else
{
valid=0;
wait();
}
}
}
SC_HAS_PROCESS(my_module);
my_module(sc_module_name name):
sc_module(name),
clk("clk"), x("x"), valid("valid")
{
SC_THREAD(work_foo);
//dont_initialize();
sensitive<<clk.pos();
valid=0;
}
};
main.cpp:
#include "systemc.h"
#include "my_module.h"
int sc_main (int argc, char* argv[])
{
sc_clock clock("clock", 10, SC_NS);
sc_signal<sc_logic > x;
my_module mm("my_mod");
mm.clk(clock);
mm.x(x);
mm.foo ();
sc_start(200, SC_NS);
sc_stop();
return 0;
}
And now I'm trying to implement it another way. I was advised to use additional sc_signal (or variable) in my module, which indicates the incrementing number of the phase. The problem is what this gets looped at the very start. How can I solve this?
#include "systemc.h"
SC_MODULE (my_module)
{
sc_in <bool> clk;
sc_out <sc_logic> x;
sc_signal <bool> valid;
sc_signal <uint> phase;
void foo()
{
valid = 1;
return;
}
void work_foo()
{
while (true)
{
if (valid == 1)
{
if (phase == 0)
{
x = SC_LOGIC_0;
phase=phase+1;
}
else if (phase == 1)
{
x = SC_LOGIC_0;
phase=phase+1;
}
else if (phase == 2)
{
x = SC_LOGIC_1;
phase=phase+1;
}
}
else
{
phase=0;
valid=0;
wait();
}
}
}
SC_HAS_PROCESS(my_module);
my_module(sc_module_name name):
sc_module(name),
clk("clk"), x("x"), valid("valid")
{
SC_THREAD(work_foo);
//dont_initialize();
sensitive<<clk.pos();
valid=0;
phase=0;
}
};

How to notify ListView that DataModel has changed

I created a ListView and I want to use it with a custom DataModel. However, I have a problem: at the moment the view gets created, I don't have the data loaded into the model. The model data is set after the view is created and when I set the data onto the model, the view doesn't update and doesn't read again the model data. This is my ListView:
ListViewCountainer.qml
Container {
// countryModelData is set after ListViewCountainer gets created
// when countryModelData gets set, the model is populated with data
property variant countryModelData
leftPadding: 20.0
rightPadding: 20.0
topPadding: 20.0
bottomPadding: 20.0
CountryDetailsListView {
id: countryDetailsListView
dataModel: CountryDataModel {
countryData: countryModelData
}
}
}
And here is my model:
countrydatamodel.h
#ifndef COUNTRYDATAMODEL_H_
#define COUNTRYDATAMODEL_H_
#include <QtCore/QAbstractListModel>
#include <QtCore/QList>
#include <QObject>
#include <QtCore/QVariant>
#include <bb/cascades/DataModel>
#include <bb/data/JsonDataAccess>
class CountryDataModel : public bb::cascades::DataModel
{
Q_OBJECT
Q_PROPERTY(QVariant countryData READ getCountryData WRITE setCountryData)
public:
CountryDataModel(QObject* parent = 0);
virtual ~CountryDataModel();
Q_INVOKABLE int childCount(const QVariantList& indexPath);
Q_INVOKABLE QVariant data(const QVariantList& indexPath);
Q_INVOKABLE bool hasChildren(const QVariantList& indexPath);
Q_INVOKABLE QString itemType(const QVariantList& indexPath);
Q_INVOKABLE void removeItem(const QVariantList& indexPath);
Q_INVOKABLE QVariant getCountryData();
Q_INVOKABLE void setCountryData(QVariant data);
private:
QVariantList m_elements;
};
#endif /* COUNTRYDATAMODEL_H_ */
countrydatamodel.cpp
#include <src/countrydatamodel.h>
#include <QtCore/QtAlgorithms>
#include <QtCore/QDebug>
#include <bb/cascades/DataModel>
#include <bb/data/JsonDataAccess>
CountryDataModel::CountryDataModel(QObject* parent) : bb::cascades::DataModel(parent)
{
}
CountryDataModel::~CountryDataModel()
{
}
bool CountryDataModel::hasChildren(const QVariantList &indexPath)
{
qDebug() << "==== CountryDataModel::hasChildren" << indexPath;
if ((indexPath.size() == 0))
{
return true;
}
else
{
return false;
}
}
int CountryDataModel::childCount(const QVariantList &indexPath)
{
qDebug() << "==== CountryDataModel::childCount" << indexPath;
if (indexPath.size() == 0)
{
qDebug() << "CountryDataModel::childCount" << m_elements.size();
return m_elements.size();
}
qDebug() << "==== CountryDataModel::childCount" << 0;
return 0;
}
QVariant CountryDataModel::data(const QVariantList &indexPath)
{
qDebug() << "==== CountryDataModel::data" << indexPath;
if (indexPath.size() == 1) {
return m_elements.at(indexPath.at(0).toInt());
}
QVariant v;
return v;
}
QString CountryDataModel::itemType(const QVariantList &indexPath)
{
Q_UNUSED(indexPath);
return "";
}
void CountryDataModel::removeItem(const QVariantList& indexPath)
{
if(indexPath.size() == 1) {
m_elements.removeAt(indexPath.at(0).toInt());
}
emit itemRemoved(indexPath);
}
QVariant CountryDataModel::getCountryData()
{
return QVariant(m_elements);
}
void CountryDataModel::setCountryData(QVariant data)
{
m_elements = data.toList();
qDebug() << "================== CountryDataModel: " << m_elements;
}
I put some debug messages in the childCount function for example and it gets called only once, which means that the ListView asks the model for the data just once, when the model is created.
Is it possible to force ListView to read again the data from the model after the model gets populated with data? Or how could I make this approach work and load the data in the view?
Thanks!
In order for the model to be updated, the setCountryData member function needs to be updated like so:
void CountryDataModel::setCountryData(QVariant data)
{
m_elements = data.toList();
emit itemsChanged(bb::cascades::DataModelChangeType::AddRemove, QSharedPointer< bb::cascades::DataModel::IndexMapper >(0));
}
FML...
You need to declare a signal for the property you want to update in backend.
Q_PROPERTY(QVariant countryData READ getCountryData WRITE setCountryData NOTIFY contryDataChanged)
add its declaration as well.
Then you say -
emit contryDataChanged();
wherever you feel like list should re-read contents. (normally setter methods).

PCL create a pcd cloud

This is what I have so far and I want to save pcd file from it
I know I have to do something like this but not exactly sure
pcl::PointCloud::PointPointXYZRGBA> cloud;
pcl::io:;savePCDFileASCII("test.pcd",cloud);
what do i have to add in my current code that i will have test.pcd
Thanks
#include <pcl/point_cloud.h>
#include <pcl/point_types.h>
#include <pcl/io/openni_grabber.h>
#include <pcl/visualization/cloud_viewer.h>
#include <pcl/common/time.h>
class SimpleOpenNIProcessor
{
public:
SimpleOpenNIProcessor () : viewer ("PCL OpenNI Viewer") {}
void cloud_cb_ (const pcl::PointCloud<pcl::PointXYZRGBA>::ConstPtr &cloud)
{
static unsigned count = 0;
static double last = pcl::getTime ();
if (++count == 30)
{
double now = pcl::getTime ();
std::cout << "distance of center pixel :" << cloud->points [(cloud->width >> 1) * (cloud->height + 1)].z << " mm. Average framerate: " << double(count)/double(now - last) << " Hz" << std::endl;
count = 0;
last = now;
}
if (!viewer.wasStopped())
viewer.showCloud (cloud);
}
void run ()
{
// create a new grabber for OpenNI devices
pcl::Grabber* interface = new pcl::OpenNIGrabber();
// make callback function from member function
boost::function<void (const pcl::PointCloud<pcl::PointXYZRGBA>::ConstPtr&)> f =
boost::bind (&SimpleOpenNIProcessor::cloud_cb_, this, _1);
// connect callback function for desired signal. In this case its a point cloud with color values
boost::signals2::connection c = interface->registerCallback (f);
// start receiving point clouds
interface->start ();
// wait until user quits program with Ctrl-C, but no busy-waiting -> sleep (1);
while (true)
boost::this_thread::sleep (boost::posix_time::seconds (1));
// stop the grabber
interface->stop ();
}
pcl::visualization::CloudViewer viewer;
};
int main ()
{
SimpleOpenNIProcessor v;
v.run ();
return (0);
}
#include <iostream>
#include <string>
#include <sstream>
#include <pcl/io/pcd_io.h>
#include <pcl/point_types.h>
#include <pcl/io/openni_grabber.h>
#include <pcl/visualization/cloud_viewer.h>
using namespace std;
const string OUT_DIR = "D:\\frame_saver_output\\";
class SimpleOpenNIViewer
{
public:
SimpleOpenNIViewer () : viewer ("PCL Viewer")
{
frames_saved = 0;
save_one = false;
}
void cloud_cb_ (const pcl::PointCloud<pcl::PointXYZRGB>::ConstPtr &cloud)
{
if (!viewer.wasStopped()) {
viewer.showCloud (cloud);
if( save_one ) {
save_one = false;
std::stringstream out;
out << frames_saved;
std::string name = OUT_DIR + "cloud" + out.str() + ".pcd";
pcl::io::savePCDFileASCII( name, *cloud );
}
}
}
void run ()
{
pcl::Grabber* interface = new pcl::OpenNIGrabber();
boost::function<void (const pcl::PointCloud<pcl::PointXYZRGB>::ConstPtr&)> f =
boost::bind (&SimpleOpenNIViewer::cloud_cb_, this, _1);
interface->registerCallback (f);
interface->start ();
char c;
while (!viewer.wasStopped())
{
//sleep (1);
c = getchar();
if( c == 's' ) {
cout << "Saving frame " << frames_saved << ".\n";
frames_saved++;
save_one = true;
}
}
interface->stop ();
}
pcl::visualization::CloudViewer viewer;
private:
int frames_saved;
bool save_one;
};
int main ()
{
SimpleOpenNIViewer v;
v.run ();
return 0;
}
Here you go.