Linking gRPC on Windows for VisualC++ - visual-studio

I am trying to use gRPC in a Visual C++ project.
So far I have:
1) Build gRPC with vcpkg: vcpkg install grpc:x64-windows
2) Integrated the vcpgk libraries with visual studio: vcpkg integrate install
So far, so good - intellisense autocompletes the namespace etc.
My client cpp file looks like this:
#include "pch.h"
#include <iostream>
#include <memory>
#include <string>
#include <grpcpp\grpcpp.h>
#include "GRPCServerInterface.grpc.pb.h"
#include "FileFormat.pb.h"
using grpc::Channel;
using grpc::ClientContext;
using grpc::Status;
using namespace GRPCServerInterface;
int main()
{
std::cout << "Hello World!\n";
// prepare send message & payload
IsFormatSupportedInput msg;
msg.set_fileextension(".asp");
// prepare reply
IsFormatSupportedOutput rpl;
// connect
FileHandler::Stub ClientStub = FileHandler::Stub(grpc::CreateChannel("localhost:50051", grpc::InsecureChannelCredentials()));
ClientContext context;
// execute rpc
Status status = ClientStub.IsFormatSupported(&context, msg, &rpl);
// handle result
if (status.ok())
{
std::cout << "Format supported says:" << std::endl << "\t formats read: " << rpl.readsupportedformats() << std::endl << "\t formats write: " << rpl.writesupportedformats() << std::endl;
}
else
{
std::cout << status.error_code() << ": " << status.error_message() << std::endl;
}
}
All messages & proto files exits and work in general, since I already use them in python and c# projects.
When building, Visual Studio generates a boatload of 125 errors, all in files I never touched.
In GRPCServerInterface.pb.h, there is identifier GOOGLE_DCHECK is undefined
All other errors are member abc may not be initialized in various header files in the grpc includes, for example
member "google::protobuf::Any::kIndexInFileMessages" may not be initialized in file any.pb.h. Many more in type.pb.h and descriptor.pbp.h.
Last but not least, I get prompted add #iclude "pch.h" to the auto-generated protobuf classes grpcserverinterface.grpc.pb.cc and grpcserverinterface.pb.cc - adding it changes a bit, but basically all errors are still undefined symbol and member may not be initialized. And I really do not want to modify auto-generated code every time.
What am I missing? Or is it just a fruitless endeavor to try using grpc with Visual Studio and should I just move to a build framework like bazel?

Solved it!
Two steps for solving:
1) I disabled precompiled headers for the whole project - this made the #include "pch.h go away. You could probalby get away with disabling it just for the protobuf files, as it can be done on a per-file basis.
2) One of the last errors listed was unresolved external symbol __imp_WSASocketA, which finally led me to this question Unresolved external symbol LNK2019. I just included #pragma comment(lib, "Ws2_32.lib") in one source file, and now everything works just perfect.

Related

Visual Studio 2022 not allowing c++20 even though i have got /std:c++20

I have got the following code:
#include<iostream>
#include<ranges>
#include<string>
auto f(auto& x, auto& y)
{
std::cout << x << y << "\n";
}
struct s
{
int x;
std::string y;
};
int main()
{
std::cout << "Hello World" << "\n";
}
and I have the /std:c++20 in my configuration:
ISO C++20 Standard (/std:c++20)
I have tried using that and I have the following error:
Severity Code Description Project File Line Suppression State
Error (active) E1598 'auto' is not allowed here Project1 C:\Users\robert\source\repos\Project1\Project1\Source.cpp 5
1>Source.cpp
1>The contents of <ranges> are available only with C++20 or later.
1>C:\Users\rober\source\repos\Project1\Project1\Source.cpp(5,15): error C3533: a parameter cannot have a type that contains 'auto'
1>C:\Users\rober\source\repos\Project1\Project1\Source.cpp(5,24): error C3533: a parameter cannot have a type that contains 'auto'
I am expecting my code to run fine because all of the c++20 headers are fine like std::ranges etc. It is by default on Visual Studio 2022 that the language is C++14 but I do not know why it is not running. So, it just resulted in the error shown above.
I have seen the other question about auto is not allowed here but that was in c++17 and the answer to that was it will come with c++20, but i have /std:c++20 in my projects -> propeties bit of visual studio 2022

libxl library use in c++

When I create a project visual studio 2015 I can work this libxl library hovewer I could not be able to work that library on visual studio qt gui application project.
I try everything whatever I know.
#include "stdafx.h"
#include "QtGuiApplication5.h"
#include <QtWidgets/QApplication>
#include <qapplication.h>
#include <qpushbutton.h>
#include <iostream>
#include <conio.h>
#include "libxl.h"
using namespacenclude <Qt libxl;
using namespace std;
int main(int argc, char *argv[])
{
Book* book = xlCreateBook();
if (book)
{
if (book->load(L"..\\Lab_Bus Datebase.xlsx"))
{
Sheet* sheet = book->getSheet(0);
if (sheet)
{
const wchar_t* s = sheet->readStr(2, 1);
if (s) std::wcout << s << std::endl << std::endl;
}
}
else
{
std::cout << "At first run generate !" << std::endl;
}
book->release();
}
std::cout << "\nPress any key to exit...";
_getch();
QApplication a(argc, argv);
QtGuiApplication5 w;
w.show();
return a.exec();
}
Link2019 error: Severity Code Description Project File Line Suppression State
Error LNK2019 unresolved external symbol __imp_xlCreateBookW referenced in function main QtGuiApplication5
link1120 error: Severity Code Description Project File Line Suppression State
Error LNK1120 1 unresolved externals QtGuiApplication5 C
You need to configure visual studio project properties to use required lib. Refer this link for the same.
You are using .xlsx file so instead of xlCreateBook use xlCreateXMLBook. Apart from this you need to use using namespace libxl;as well
Below are Factory functions:
Book* xlCreateBook()
Create a binary book instance for xls format. This function should be called first for receiving a book pointer. This function and other classes are in libxl namespace.
Book* xlCreateXMLBook()
Create a xml book instance for xlsx format. This function should be called first for receiving a book pointer. This function and other classes are in libxl namespace.
See below image above code works fine at my machine.

SIGINT was not declared in this scope

Background
I am trying to build a sample REST api app for Rasbian running on Raspberry 3. I used cpprestsdk.
Sample contains the following header file:
#include <condition_variable>
#include <mutex>
#include <iostream>
static std::condition_variable _condition;
static std::mutex _mutex;
namespace cfx {
class InterruptHandler {
public:
static void hookSIGINT() {
signal(SIGINT, handleUserInterrupt);
}
static void handleUserInterrupt(int signal){
if (signal == SIGINT) {
std::cout << "SIGINT trapped ..." << '\n';
_condition.notify_one();
}
}
static void waitForUserInterrupt() {
std::unique_lock<std::mutex> lock { _mutex };
_condition.wait(lock);
std::cout << "user has signaled to interrup program..." << '\n';
lock.unlock();
}
};
}
Issue
When compiling on MacOS, no problem occurs.
When compiling in rasbian however, I get error: 'SIGINT' was not declared in this scope error.
It is clear that SIGINT definition - #define SIGINT 2 or similar - is not reachable when compiling on rasbian.
Question
Why I am getting this error on rasbian but not on macOS? Is it because compiler cannot locate signal.h?
I made sure that include_directories in CMakeLists.txt contains required include paths.
UPDATE
Error resolved when I manually added #include <csignal>.
You haven't included signal.h.
You're including some C++ standard library headers, and as a side effect on MacOS, these happen to include signal.h. However, that isn't specified to happen so you can't rely on it working in different implementations of those headers.
Try adding:
#include <signal.h>
at the top.
On Linux the header file to include is
#include <signal.h>
On MacOS the equivalent header file to include is
#include <csignal.h>
Depending on your OS, header files always change. They should both do the same thing though

UpdateDriverForPlugAndPlayDevices error is telling me I'm *not* doing something that I am

I'm working on a means of installing a driver. Because of the multiple platforms on which this must work, I'm shelling-out to both devcon and dpinst to do the work of driver install/update/removal when needed. While testing, I'm having problems with the shelling out to devcon. To isolate, I wrote a small app to do what devcon does in update see here, using the devcon source from the WinDDK for reference. I'm having some problems with UpdateDriverForPlugAndPlayDevices() from Setup API (actually part of Newdev.dll) see here. The source code is here:
#include <iostream>
#include <Windows.h>
#include <newdev.h>
int main(int argc, char** argv) {
// Go through the same steps as does dev con for this update crap
char infFile[MAX_PATH];
if(3 > argc) {
std::cerr << "an INF and HW ID must be specified" << std::endl;
return 1;
}
DWORD result(GetFullPathName(argv[1], MAX_PATH, infFile, NULL));
if((result >= MAX_PATH) || (0 == result)) {
std::cerr << "path is too long for buffer" << std::endl;
return 1;
}
if(GetFileAttributes(infFile) == -1) {
std::cerr << "file doesn't exist" << std::endl;
return 1;
}
BOOL reboot(FALSE);
if(!UpdateDriverForPlugAndPlayDevices(NULL, argv[2], infFile, INSTALLFLAG_FORCE, &reboot)) {
std::cerr << "Failed to install the driver. Code: "
<< GetLastError()
<< std::endl;
return 2;
}
if(reboot) {
std::cout << "A reboot is needed to complete driver install"
<< std::endl;
}
return 0;
}
The program fails when UpdateDriverForPlugAndPlayDevices() returns false. This then prints the error code, returned by GetLastError(), so I'd know what went wrong. The error code returned: 259. According to this resource says this is ERROR_NO_MORE_ITEMS. According to the link for UpdateDriverForPlugAndPlayDevices(), this function returns this error code when, "The function found a match for the HardwareId value, but the specified driver was not a better match than the current driver and the caller did not specify the INSTALLFLAG_FORCE flag." You'll notice from my code that I did specify this flag.
I do not know where to go from here. Can someone please identify from this code what it is I'm missing? This just has the "feel" of something simple, but I'm totally missing it.
Thank you,
Andy
The problem appeared to be not with the code but with the INF file. Interesting that the documentation for the function said that using that flag will force the install but didn't when the INF file didn't "list" any device classes in the models section. This is how I was able to install eventually. I added the correct device class to the models section in the INF.
EDIT Sep. 17, 2020
It was requested by someone just today (of the edit) to add an example from the INF. It's been 8 years since I had this issue and I no longer work for this team. However, as best as I can recall, and drawing heavily upon the docs for INF Models Section and INF Manufacturers Section, I hope this helps.
Essentially, the class is specified by the Models Section and the model is specified by the Manufacturer Section.
[Manufacturer]
%MfgName%=Standard,NTamd64
[Standard.NTamd64]
%DeviceString%=<class path or GUID>\<device>
[Strings]
MfgName=ACME
DeviceString="Device Type"

How to display a #defined constant during build, in Visual Studio 2010?

I've seen this, but none of the answers worked for VS2010. The constant's (or should I call it variable?) numerical value didn't get displayed
This line of code #if OGRE_PLATFORM == OGRE_PLATFORM_LINUX is turning out to be true when I'm actually programming in windows. I need to see the value of OGRE_PLATFORM_WIN32 and OGRE_PLATFORM_LINUX during the build process itself. Could you help with how to go about it?
You can check the preprocessor output using:
/E - preprocess to stdout or
/P - preprocess to file or
/EP - preprocess to stdout without #line directives
options in visual studio
First, check the preprocessor defines in project options - active configuration and all configurations, and make sure the right things are defined.
If you are still having problems, try substituting this for your main method:
#include <iostream>
int main()
{
#ifdef OGRE_PLATFORM_LINUX
std::cout << "OGRE_PLATFORM_LINUX = " << OGRE_PLATFORM_LINUX << "\n";
#else
std::cout << "OGRE_PLATFORM_LINUX not defined.\n";
#endif
#ifdef OGRE_PLATFORM_WIN32
std::cout << "OGRE_PLATFORM_WIN32 = " << OGRE_PLATFORM_WIN32 << "\n";
#else
std::cout << "OGRE_PLATFORM_WIN32 not defined.\n";
#endif
#ifdef OGRE_PLATFORM
std::cout << "OGRE_PLATFORM = " << OGRE_PLATFORM << "\n";
#else
std::cout << "OGRE_PLATFORM not defined.\n";
#endif
return 0;
}
Also, did you create the project, was it created by some type of pre-make (CMake, automake, etc) system, did you download it from somewhere? If you didn't create it, somebody could have ported over some Linux code without checking their preprocessor options.

Resources