Hello I am getting the above error for the subscriber class I created as following:
The error seems in the write function of the class but I am not sure what I am missing in the function.
`uvm_analysis_imp_decl(_bfm2dut_change)
class checker_subscriber extends uvm_subscriber;
uvm_analysis_imp_bfm2dut_change#(setup_pcie_pkg::dut2bfm_hdr_trans, checker_subscriber) bfm2dut_change_ap;
`uvm_component_utils(checker_subscriber)
extern function new(string name = "checker_subscriber", uvm_component parent = null);
// BUILD,CONNECT and RUN Phase
extern virtual function void build_phase(uvm_phase phase);
extern virtual function void connect_phase(uvm_phase phase);
extern virtual task run_phase(uvm_phase phase);
// write function xal2fb
virtual function void write_xal2fb_change(xal2fb_uvc::transaction tr);
xal2fb_uvc::tx_default_data_obj obj;
$cast(obj, tr.tx_data_obj);
`uvm_info("xal2fb PPMSU monitoring", $sformatf("%m"), UVM_LOW)
monitor_xal2fb_pcie_order_check(obj);
endfunction: write_xal2fb_change
endclass : checker_subscriber
You should implement the pure virtual function void write(T t); which inherits from uvm_subscriber class in your checker_subscriber class.
Please refer to verification-methodology-reference
And assure your "write..." method's suffix matches the one you are using in macro declaration and then in the port declaration.
Related
I am trying to use a simple thread pool example from the book of Anthony Williams "C++ Concurrency in Action". I have even found the code here (the class thread_pool) in one of the posts:
Synchronizing tasks
but I have a different question. I would like to submit a task (a member function) to the queue with the following signature:
class A;
class B;
bool MyClass::Func(A*, B*);
How would I need to change the thread_pool class, or how do I pack my function in some void F(), which is assumed to be used as a task in this example?
Here is the most relevant part of the class for me (for the details please see the link above):
class thread_pool
{
thread_safe_queue<std::function<void()> work_queue; // bool MyClass::Func(a,b) ??
void worker_thread() {
while(!done) {
std::function<void()> task;
if(work_queue.try_pop(task)) {
task(); // how should my function MyClass::Func(a,b) be called here?
}
else {
std::this_thread::yield();
}
}
}
// -- Submit a task to the thread pool
template <typename FunctionType>
void submit(FunctionType f) {
work_queue.push(std::function<void()>(f)); // how should bool MyClassFunc(A*, B*) be submitted here
}
}
And finally, how can I call the submit Function in my code?
Thank you very much for your help (unfortunatelly I am not very experienced yet in using all the C++11 features, which is probably also why I need help here, but an answer to this question would be something to start with :)).
You have to bind the parameters to a value when you insert a task into the queue. That means that you have to create a wrapper for your function that stores the values for this and the values for the two function parameters. There are many ways to do this, e.g. lambda functions or std::bind.
work_queue.push_back( [obj, a, b]() {obj->Func(a,b)} );
work_queue.push_back( std::bind(&MyClass::Func, obj, a, b) );
Your submit function must take these parameters and create the binding, e.g.
template<typename F, typename... Args>
void submit(F f, Args&&... args) {
work_queue.push_back( std::bind(f, std::forward<Args>(args)...) );
}
It may be convenient to create a special overload for member functions and objects.
I've written something that does something (very) similar to this before. I'll post the code here and you can have a look. GenCmd is the function wrapper. The queue looks like this, and is used/defined in Impl (code omitted). You only need to look at implementation of GenCmd, as this contains the necessary work.
ConcurrentQueue<std::unique_ptr<Cmd>> cqueue_;
I've wrapped std::function<> to be polymorphic in queue. std_utility contains make_index_sequence, that is used to extract values from a tuple (google make_index_sequence to find an implementation somewhere if this is not already part of your std library).
#include <functional>
#include <memory>
#include <iostream>
#include <utility>
#include <boost/noncopyable.hpp>
class CmdExecutor : public boost::noncopyable
{
public:
CmdExecutor(std::ostream& errorOutputStream);
~CmdExecutor();
template <class Receiver, class ... FArgs, class ... CArgs >
void process(Receiver& receiver, void (Receiver::*f)(FArgs...), CArgs&&... args)
{
process(std::unique_ptr<Cmd>(new GenCmd<void(Receiver,FArgs...)>(f, receiver, std::forward<CArgs>(args)...)));
}
private:
class Cmd
{
public:
virtual void execute() = 0;
virtual ~Cmd(){}
};
template <class T> class GenCmd;
template <class Receiver, class ... Args>
class GenCmd<void(Receiver, Args...)> : public Cmd
{
public:
template <class FuncT, class ... CArgs>
GenCmd(FuncT&& f, Receiver& receiver, CArgs&&... args)
: call_(std::move(f)),
receiver_(receiver),
args_(args...)
{
}
//We must convert references to values...
virtual void execute()
{
executeImpl(std::make_index_sequence<sizeof...(Args)>{});
}
private:
template <std::size_t ... Is>
void executeImpl(std::index_sequence<Is...>)
{
// We cast the values in the tuple to the original type (of Args...)
call_(receiver_, static_cast<Args>(std::get<Is>(args_))...);
}
std::function<void(Receiver&, Args...)> call_;
Receiver& receiver_;
// NOTE:
// References converted to values for safety sake, as they are likely
// to not be around when this is executed in other context.
std::tuple<typename std::remove_reference<Args>::type...> args_;
};
void process(std::unique_ptr<Cmd> command);
class Impl;
Impl* pimpl_;
};
It's basically used as follows:
...
CmdExecutor context_;
...
void MyClass::myFunction()
{
ArgX x;
ArgY y;
context_.process(*this, &MyClass::someFunction, x, y);
}
You can see from this that process does the wrapping of member function type and converts it to the underlying type for storage on queue. This allows for multiple argument types. I've opted for using runtime polymorphism to store the function types, hence the GenCmd derivative.
Note: If the invoked function receives an rvalue (Arg&&), the stored type is casted to the original type, therefore causing a move, and rendering the applicable command argument (which would only be invoked once) empty (that's the intent, at least - untested...)
I'm working on a student project. It's a network card game. The solution contains 3 projects. Client's GUI using Windows Forms so it has managed classes. Static client's library in native C++. GUI's project has reference to it thus uses 'Mixed Rules'. Server is in native C++ as well. I use RPC middleware for communication. It works only with native C++. That is why I need the static library to hide there all the details of communication on client's side.
Since the server can at any moment change its state and that should be shown in client's GUI, I use callback approach to change Windows Forms' components. And here I found a problem because I need to change private members of managed class with the help of a native object.
There are probably different ways to do that. My idea is sending a pointer to instance of managed class into instance of native class and saving it there. So later I can call from that native object public member functions of that managed class to change components.
This is from my 'Mixed Rules' GUI project:
//Native class for changing window 'Lobby'
class LobbyI : public ClientLib::Lobby {
public:
LobbyI();
~LobbyI();
//Should change window due to current Server's state
void reDraw(const CommonLogic::ServerState&);
};
// Managed class implements GUI for window 'Lobby'
// generated by Visual Studio designer
public ref class LobbyGUI : public System::Windows::Forms::Form {
//My members
ClientLib::Mediator* mediatorPtr; // Is it correct?
LobbyI* lobbyPtr; // ?
public:
LobbyGUI(void) {
InitializeComponent();
mediatorPtr = new ClientLib::Mediator(); // Is it correct?
lobbyPtr = new LobbyI(); // ?
mediatorPtr->setCallback(lobbyPtr);
}
protected:
~LobbyGUI() {
if (components) { delete components; }
delete lobbyPtr; // Is it correct?
lobbyPtr = nullptr; // ?
delete mediatorPtr; // ?
mediatorPtr = nullptr; // ?
}
private: System::Windows::Forms::Button^ buttonLogIn;
//...
This is from native static library ClientLib:
class Lobby {
public:
virtual ~Lobby();
virtual void reDraw(const CommonLogic::ServerState&) = 0;
};
class Mediator {
CommonLogic::ServerState serverState;
Lobby* lobbyPtr;
public:
Mediator();
~Mediator();
void setCallback(Lobby* ptr) { lobbyPtr = ptr; }
void reDrawLobby() { lobbyPtr->reDraw(serverState); }
};
This code builds ok. The only thing I need now is that the member function reDraw() of native derived class LobbyI is able to change the window implemented by managed class LobbyGUI. Thus getting and keeping and using pointer to it. And then I think it all will work. How to do that?
Maybe it's not the nicest implementation in general. I would be happy to read other suggestion.
I'm also doubtful about the way I used pointers to native classes inside managed class. Is it correct? It didn't work correct until I inserted ptr=nullptr; after delete ptr; in destructor.
UPDATE: Now I see redundancy in my code. Abstract class Lobby is useless. I need only to implement reDraw() function in managed class which will have obviously access to components of the window. And then pass safe pointer to native class function which expects pointer to a function as a parameter.
Finally I've solved it!! Using this article. In the following code a native object stores provided pointer to a function of managed object. So this callback function can be invoked at any time. A delegate is used as a form of type-safe function pointer. Instance of GCHandle is used to prevent the delegate from being relocated by garbage collector.
Here is simple CLR Console Application which increments and prints some integer using callback function invoked from native object. Thus we can "change private members of managed object using a native one".
using namespace System;
using namespace System::Runtime::InteropServices;
typedef void(__stdcall *ANSWERCB)(); // define type of callback function
#pragma unmanaged
class NativeClass {
ANSWERCB cbFuncPtr = 0; // pointer to callback function
public:
void setCallback(ANSWERCB fptr) {
cbFuncPtr = fptr;
incAndPrint();
}
void incAndPrint() { cbFuncPtr(); } // invokes callback which increments and prints
};
#pragma managed
ref class ManagedClass {
public: delegate void Del();
private:
Int32 i;
NativeClass* nativePtr;
Del^ delHandle;
GCHandle gch;
public:
ManagedClass(Int32 ii) : i(ii) {
nativePtr = new NativeClass;
delHandle = gcnew Del(this, &ManagedClass::changeAndPrintInt);
gch = GCHandle::Alloc(delHandle);
IntPtr ip = Marshal::GetFunctionPointerForDelegate(delHandle);
ANSWERCB callbackPtr = static_cast<ANSWERCB>(ip.ToPointer());
nativePtr->setCallback(callbackPtr);
}
~ManagedClass() {
delete nativePtr;
nativePtr = __nullptr;
gch.Free();
}
private:
void changeAndPrintInt() // callback function
{
Console::WriteLine(++i);
}
};
int main(array<System::String ^> ^args)
{
ManagedClass mc(1);
return 0;
}
I'm writing in c++ a graphic user interfaced program and I need to create a threads in the program.
so I'm using System::Threading namespace to get my goal.
The function that I want to use as thread is a class member function, so here is what I've done:
Server::Server() // constructor
{
System::Threading::Thread^ T = gcnew System::Threading::Thread(gcnew System::Threading::ThreadStart(this, this->RunServer)); // Server::RunServer
T->Start();
}
since it gave me those errors:
Error 2 error C3350: 'System::Threading::ThreadStart' : a delegate
constructor expects 2 argument(s)
Error 1 error C3867: 'Server::RunServer': function call missing
argument list; use '&Server::RunServer' to create a pointer to
member
I tried this call:
Server::Server() // constructor
{
System::Threading::Thread^ T = gcnew System::Threading::Thread(gcnew System::Threading::ThreadStart(&Server::RunServer));
T->Start();
}
and received this errors:
Error 1 error C3364: 'System::Threading::ThreadStart' : invalid
argument for delegate constructor; delegate target needs to be a
pointer to a member
function
2 IntelliSense: invalid delegate initializer -- function is not a
member of a managed
class
as far as I know the second try did not succeed because Server::RunServer doesn't have address, so it's like to do &1.
by the way I tried to use the ThreadStart to create thread of none class memeber function and it worked fine.
I'm using win7 - visual studio 2012. How to make it work?
EDIT:
Server declaration:
class Server
{
public:
/* Fields */
std::string Port;
std::string Host;
WSADATA wsaData;
int ListenResult;
SOCKET ListenSocket;
SOCKET* ClientSocket;
SOCKADDR_IN* ADDR;
int ADDRSize;
struct addrinfo *result;
struct addrinfo hints;
std::vector<Client> Clients;
/* Methods */
Server();
std::wstring StringW(char* String);
void Print(std::wstring String);
std::wstring CurrentTime();
void ParseServerIni();
void RunServer();
void PartToString(Part* _Part);
void InsertListItem(std::string String);
void ClientHandler(SOCKET* _Sock, SOCKADDR_IN* _ADDR);
int ParsePacket(Packet &_Packet, int _Bytes, Byte** _PacketBlock);
};
You almost got the syntax right.
Assuming the declaration is:
public ref class Server
{
void RunServer();
};
Then you should combine your two approaches, by specifying both the object to invoke the method on, and the address of the method, with the name of the declaring class.
gcnew System::Threading::ThreadStart(this, &Server::RunServer)
I've subclassed my Qthread so I can implement my code in run() method. I have to pass it some parameters,
I tried it like this, so what's wrong in here?
class QMyThread :
public QThread
{
public:
QMyThread();
~QMyThread(void);
virtual void start(FILE *data, int sock, int bits);
protected:
virtual void run(FILE *data, int sock, int bits);
};
run method;
void QMyThread::run(FILE *data, int sock, int bits)
{
//do stuff
}
start the thread:
QMyThread *thread;
thread->start(datafile, sockint, bitsint);
first it says the thread might not be initialized and then it crashes in the start() method with SIGSEGV error. Anyone can help me?
You shouldn't be subclassing the QThread class as this is no longer the recommended way of using QThread.
For more information http://qt-project.org/doc/qt-4.8/qthread.html
To answer your question, couldn't you just make those parameters members of your class and assign their values through setters or its contructor?
You should do this instead:
QMyThread thread;
thread.start(...)
You created a pointer to a thread and did not new it. I frankly see no reason for a pointer here, you can just create a normal variable and call a method on it.
If you do want a pointer, then use std::unique_ptr in C++11 or boost::unique_ptr
std::unique_ptr<QMyThread> thread;
thread->start(...);
EDIT:
You should really just create a QThread * thread = new QThread(this); as per the documentation.
How about using the QMetaObject class to pass the parameters to worker class. You can try like this:
QMetaObject::invokeMethod(worker, "methodName", Q_ARG(QString, "ParameterQStringValue");
Note this method will work if methodName is a slot and you use the new way of creating threads: https://mayaposch.wordpress.com/2011/11/01/how-to-really-truly-use-qthreads-the-full-explanation/
You can specify different parameters using Q_ARG macro up to 9 (http://doc.qt.io/qt-5/qmetaobject.html#details). If you need more parameters, then I suggest you to create the QVector with a structure and pass it to QMetaObject::invokeMethod as the parameter.
I am creating a thread using this call:
m_pThread=AfxBeginThread(read_data,(LPVOID)hSerial);
read_data is a static method in my class.
But I want to call a non static method and make a thread.
As I want to share a variable between this thread and one of my class method.
I tried taking a static variable but it gave some errors.
You cannot create a thread using a non-static member of a function as the thread procedure: the reason is all non-static methods of a class have an implicit first argument, this is pointer this.
This
class foo
{
void dosomething();
};
is actually
class foo
{
void dosomething(foo* this);
};
Because of that, the function signature does not match the one you need for the thread procedure. You can use a static method as thread procedure and pass the this pointer to it. Here is an example:
class foo
{
CWindThread* m_pThread;
HANDLE hSerial;
static UINT MyThreadProc(LPVOID pData);
void Start();
};
void foo::Start()
{
m_pThread=AfxBeginThread(MyThreadProc,(LPVOID)this);
}
UINT foo::MyThreadProc(LPVOID pData)
{
foo* self = (foo*)pData;
// now you can use self as it was this
ReadFile(self->hSerial, ...);
return 0;
}
I won't repeat what Marius said, but will add that I use the following:
class foo
{
CWindThread* m_pThread;
HANDLE hSerial;
static UINT _threadProc(LPVOID pData);
UINT MemberThreadProc();
void Start();
};
void foo::Start()
{
m_pThread=AfxBeginThread(_threadProc,(LPVOID)this);
}
UINT foo::MyThreadProc(LPVOID pData)
{
foo* self = (foo*)pData;
// call class instance member
return self->MemberThreadProc();
}
UINT foo::MemberThreadProc()
{
// do work
ReadFile(hSerial, ...);
return 0;
}
I follow this pattern every time I use threads in classes in MFC apps. That way I have the convenience of having all the members like I am in the class itself.