TYPE_E_LIBNOTREGISTERED(Library not registered) while call Invoke() of unregistered ActiveX control? - activex

Code as below. How to avoid the TYPE_E_LIBNOTREGISTERED(hr=0x8002801D, Library not registered) error(DO NOT register the ActiveX to Windows) of disp->Invoke()?
When register the ActiveX control, all is OK, but I want not register to WINDOWS.
Thanks!
#define WIN32_LEAN_AND_MEAN
#include <tchar.h>
#include <Windows.h>
#include <assert.h>
#include <stdio.h>
#include <ole2.h>
int APIENTRY _tWinMain(HINSTANCE hInstance,
HINSTANCE hPrevInstance, LPTSTR lpCmdLine, int nCmdShow)
{
OleInitialize(NULL);
LPCTSTR lpFile = _T("D:\\Temp\\Flash32_11_4_402_287.ocx");
HMODULE hDll = LoadLibrary(lpFile);
if (hDll)
{
typedef HRESULT (WINAPI *DllGetClassObject_t)(REFCLSID, REFIID, LPVOID*);
DllGetClassObject_t DllGetClassObject = NULL;
DllGetClassObject = (DllGetClassObject_t)GetProcAddress(hDll, "DllGetClassObject");
if (DllGetClassObject)
{
CLSID clsid = GUID_NULL;
IClassFactory *pCF = NULL;
if (SUCCEEDED(CLSIDFromString(L"{D27CDB6E-AE6D-11CF-96B8-444553540000}", &clsid))
&& SUCCEEDED(DllGetClassObject(clsid, IID_IClassFactory, (void**)&pCF)))
{
IOleObject *obj = NULL;
IDispatch *disp = NULL;
if (SUCCEEDED(pCF->CreateInstance(NULL, IID_IOleObject, (void**)&obj))
&& SUCCEEDED(obj->QueryInterface(IID_IDispatch, (void**)&disp)))
{
DISPPARAMS params = { NULL, NULL, 0, 0 };
HRESULT hr = disp->Invoke(0x70, IID_NULL,
LOCALE_USER_DEFAULT, DISPATCH_METHOD,
&params, NULL, NULL, NULL);
assert(SUCCEEDED(hr));
//ERROR: hr=0x8002801D,TYPE_E_LIBNOTREGISTERED, Library not registered
}
if (disp) disp->Release();
if (obj) obj->Release();
pCF->Release();
}
}
}
OleUninitialize();
return 0;
}

To Hans Passant:
Thanks very very much. English is not my mother tongue, but under you detailed answers, I have the perfect solution to this problem, and this is my first question on stackoverflow, thanks again. As you said, my solution is bellow:
//ITypeInfo *m_ti = NULL;
//pCF->CreateInstance(...);
ITypeLib *tl = NULL;
if (SUCCEEDED(LoadTypeLib(wsOcxFile, &tl)))
{
if (SUCCEEDED(tl->GetTypeInfoOfGuid(guid, &m_ti)))
{
hr = m_ti->Invoke(disp,
dispid, wFlags, &m_dispParams,
pvResult, &ei, &nArgErr);
}
tl->Release();
}
//m_ti->Release();

Related

read event never triggered, using libevent

I just write an echo server using libevent, but it seems that the read event is never triggered. The code is:
#include <unistd.h>
#include <stdio.h>
#include <string.h>
#include <stdlib.h>
#include <netinet/tcp.h>
#include <event.h>
#include <event2/event.h>
#include <sys/types.h>
#include <sys/socket.h>
#include <errno.h>
#include <fcntl.h>
#include <netinet/in.h>
#include <arpa/inet.h>
static short ListenPort = 19999;
static long ListenAddr = INADDR_ANY;//任意地址,值就是0
static int MaxConnections = 1024;
static int ServerSocket;
static struct event ServerEvent;
int SetNonblock(int fd)
{
int flags;
if ((flags = fcntl(fd, F_GETFL)) == -1) {
return -1;
}
if (fcntl(fd, F_SETFL, flags | O_NONBLOCK) == -1) {
return -1;
}
return 0;
}
void ServerRead(int fd, short ev, void *arg)
{
//1)when telnet on 1999 and send a string,this never prints,help!
printf("client readble\n");
fflush(stdout);
struct client *client = (struct client *)arg;
u_char buf[8196];
int len, wlen;
len = read(fd, buf, sizeof(buf));
if (len == 0) {
printf("disconnected\n");
close(fd);
event_del(&ServerEvent);
free(client);
return;
} else if (len < 0) {
printf("socket fail %s\n", strerror(errno));
close(fd);
event_del(&ServerEvent);
free(client);
return;
}
wlen = write(fd, buf, len);//1)client str never echo back
if (wlen < len) {
printf("not all data write back to client\n");
}
}
void ServerWrite(int fd, short ev, void *arg)
{
//2)to be simple,let writer do nothing
/* if(!arg)
{
printf("ServerWrite err!arg null\n");
return;
}
int len=strlen(arg);
if(len <= 0)
{
printf("ServerWrite err!len:%d\n",len);
return;
}
int wlen = write(fd, arg, len);
if (wlen<len) {
printf("not all data write back to client!wlen:%d len:%d \n",wlen,len);
}
*/
return;
}
void ServerAccept(int fd, short ev, void *arg)
{
int cfd;
struct sockaddr_in addr;
socklen_t addrlen = sizeof(addr);
int yes = 1;
cfd = accept(fd, (struct sockaddr *)&addr, &addrlen);
if (cfd == -1) {
//3)this prints ok
printf("accept(): can not accept client connection");
return;
}
if (SetNonblock(cfd) == -1) {
close(cfd);
return;
}
if (setsockopt(cfd, IPPROTO_TCP, TCP_NODELAY, &yes, sizeof(yes)) == -1) {
printf("setsockopt(): TCP_NODELAY %s\n", strerror(errno));
close(cfd);
return;
}
event_set(&ServerEvent, cfd, EV_READ | EV_PERSIST, ServerRead, NULL);
event_set(&ServerEvent, cfd, EV_WRITE| EV_PERSIST, ServerWrite,NULL);
event_add(&ServerEvent, NULL);
printf("Accepted connection from %s \n", (char *)inet_ntoa(addr.sin_addr));
}
int NewSocket(void)
{
struct sockaddr_in sa;
ServerSocket = socket(AF_INET, SOCK_STREAM, 0);
if (ServerSocket == -1) {
printf("socket(): can not create server socket\n");
return -1;
}
if (SetNonblock(ServerSocket) == -1) {
return -1;
}
memset(&sa, 0, sizeof(sa));
sa.sin_family = AF_INET;
sa.sin_port = htons(ListenPort);
sa.sin_addr.s_addr = htonl(ListenAddr);
if (bind(ServerSocket, (struct sockaddr*)&sa, sizeof(sa)) == -1) {
close(ServerSocket);
printf("bind(): can not bind server socket");
return -1;
}
if (listen(ServerSocket, MaxConnections) == -1) {
printf("listen(): can not listen server socket");
close(ServerSocket);
return -1;
}
event_set(&ServerEvent, ServerSocket, EV_READ | EV_PERSIST, ServerAccept, NULL);
if (event_add(&ServerEvent, 0) == -1) {
printf("event_add(): can not add accept event into libevent");
close(ServerSocket);
return -1;
}
return 0;
}
int main(int argc, char *argv[])
{
int retval;
event_init();
retval = NewSocket();
if (retval == -1) {
exit(-1);
}
event_dispatch();
return 0;
}
The server is tested using Telnet, but the client receives nothing.
The question details are posted as comments in the code above, at 1)、2)、3).
Can someone help me find out why the read event is never triggered?
basically you should not set the accepted socket as EV_WRITE until you actually want to write to the socket. You are telling libevent "let me know when I can write to this socket", which is pretty much always. So ServerWrite is being called in a tight loop. In practice the only time you need EV_WRITE is if you are writing a buffer but all of the bytes are not written. You then need to save the unwritten portion of the buffer and use EV_WRITE to signal when the socket can be written to again.

Directx Window keeps Crashing

My problem with this code is that when I run it in visual C++ A window pops up
but then it just crashes. It is not responding and I cannot click exit. I have to pull up the
task manager to get rid of the window. I am new to windows programming and direct X.
Below I will post were I think the problem is.
#include <d3d9.h>
#include <time.h>
#define APPTITLE "Direct3D_Windowed"
LRESULT WINAPI WinProc(HWND, UINT, WPARAM, LPARAM);
ATOM MyRegisterClass(HINSTANCE);
int Game_Init(HWND);
void GAME_RUN(HWND);
void GAME_END(HWND);
LPDIRECT3D9 d3d = NULL;
LPDIRECT3DDEVICE9 d3ddev = NULL;
// Over here, after GAME_END() is called, I tried separating the POSTQUITMESSAGE But I
I just got an error.
LRESULT WINAPI WinProc(HWND hWnd, UINT msg, WPARAM wParam, LPARAM lParam)
{
switch(msg )
{
case WM_DESTROY:
GAME_END(hWnd);
PostQuitMessage(0);
return 0;
}
return DefWindowProc(hWnd, msg, wParam, lParam);
}
ATOM MyRegisterClass(HINSTANCE hInstance)
{
WNDCLASSEX wc;
wc.cbSize = sizeof(WNDCLASSEX);
wc.style = CS_HREDRAW | CS_VREDRAW;
wc.lpfnWndProc = (WNDPROC)WinProc;
wc.cbClsExtra = 0;
wc.cbWndExtra = 0;
wc.hInstance = hInstance;
wc.hIcon = NULL;
wc.hCursor = LoadCursor(NULL, IDC_ARROW);
wc.hbrBackground = (HBRUSH)GetStockObject(WHITE_BRUSH);
wc.lpszMenuName = NULL;
wc.lpszClassName = APPTITLE;
wc.hIconSm = NULL;
return RegisterClassEx(&wc);
}
// I got this code from a book that I am reading and realized that WinProc is not being
called in this function. Is this the potential problem? Were would I put the WinProc
function call if it is supposed to be here in WinMain
int WINAPI WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, LPSTR lpCmdLine, int nCmdShow)
{
MSG msg = {0};
MyRegisterClass(hInstance);
HWND hWnd;
hWnd = CreateWindow(
APPTITLE,
APPTITLE,
WS_OVERLAPPEDWINDOW,
CW_USEDEFAULT,
CW_USEDEFAULT,
500,
400,
NULL,
NULL,
hInstance,
NULL);
if(!hWnd)
return FALSE;
ShowWindow(hWnd, nCmdShow);
UpdateWindow(hWnd);
if(!Game_Init(hWnd))
return 0;
int done = 0;
while(!done)
{
if(msg.message == WM_QUIT)
{
if(PeekMessage(&msg, NULL, 0, 0, PM_REMOVE))
{
MessageBox(hWnd, "Recieve WM_QUIT message", "WinMain", MB_OK);
done = 1;
}
TranslateMessage(&msg);
DispatchMessage(&msg);
}
else
GAME_RUN(hWnd);
}
return msg.wParam;
}
int Game_Init(HWND hWnd)
{
MessageBox(hWnd, "Program is about to start", "Game_Init", MB_OK);
d3d = Direct3DCreate9(D3D_SDK_VERSION);
if(d3d == NULL)
{
MessageBox(hWnd, "Error initializing Direct3D", "Error", MB_OK);
return 0;
}
D3DPRESENT_PARAMETERS d3dpp;
ZeroMemory(&d3dpp, sizeof(d3dpp));
d3dpp.Windowed = TRUE;
d3dpp.SwapEffect = D3DSWAPEFFECT_DISCARD;
d3dpp.BackBufferFormat = D3DFMT_UNKNOWN;
d3d->CreateDevice(
D3DADAPTER_DEFAULT,
D3DDEVTYPE_HAL,
hWnd,
D3DCREATE_SOFTWARE_VERTEXPROCESSING,
&d3dpp,
&d3ddev);
if(d3ddev == NULL)
{
MessageBox(hWnd, "Error creating Direct device", "Error", MB_OK);
return 0;
}
srand(time(NULL));
return 1;
}
void GAME_RUN(HWND hWnd)
{
if(d3ddev == NULL)
return;
d3ddev->Clear(0, NULL, D3DCLEAR_TARGET, D3DCOLOR_XRGB(0, 255, 255), 1.0f, 0);
if(d3ddev->BeginScene())
{
d3ddev->EndScene();
}
d3ddev->Present(NULL, NULL, NULL, NULL);
}
void GAME_END(HWND hWnd)
{
MessageBox(hWnd, "Program is about to end", "Game End", MB_OK);
if(d3ddev != NULL)
d3ddev->Release();
if(d3d != NULL)
d3d->Release();
}
Have a look at this?
if(msg.message == WM_QUIT)
In your while-loop.
Perhaps change that to, say:
if(true)
Reason: you want your application to pass on all messages, not just the ones that cause it to quit. Say for instance when windows wants your application to draw itself. Basically, your current code doenst allow your application to do anything except quitting.
If you want to do something special when the application quits, add another case WM_QUIT: after the already existing case WM_DESTROY: in WinProc().
The current location for GAME_RUN(hWnd); will not work out for you.
You want to either put that in a seperate thread (easiest, and highest performance). Or you want to use some timers, and handle it with case WM_TIMER: after your case WM_DESTROY:. Or alternatively make up your own user defined message.

glib-2.0: g_spawn_command_line_sync() - unknown stdout length

function g_spawn_command_line_sync() has argument "gchar **standard_output":
https://developer.gnome.org/glib/stable/glib-Spawning-Processes.html#g-spawn-command-line-sync
I need read binary data from standard_output, but I not known length of standard_output.
Function g_spawn_command_line_sync():
http://fossies.org/dox/glib-2.38.2/gspawn-win32_8c_source.html#l01452
execute:
GString *outstr = NULL;
*standard_output = g_string_free (outstr, FALSE);
Struct GString include "gsize len", but g_spawn_command_line_sync() accessible only "gchar **".
I have next solution. I write size of stdout to stderr, which not using.
Example code:
#include <stdio.h>
#include <stdlib.h>
#include <glib.h>
int main()
{
gint exit_status = 0;
gchar *p_stdout = NULL;
gchar *p_stderr = NULL;
GError *p_error = NULL;
gboolean result;
result = g_spawn_command_line_sync("./make_image.py", &p_stdout, &p_stderr, &exit_status, &p_error);
if (!result) {
if (p_error != NULL) {
printf(p_error->message);
}
else {
printf("ERROR: Command not run\n");
}
}
else if (exit_status != 0) {
printf(p_stderr);
}
else {
int size = atoi(p_stderr);
gchar *p_c = p_stdout;
for (int i = 0; i < size; ++i) {
fputc(*p_c++, stdout);
}
//printf(p_stdout);
}
if (p_stdout) {
g_free(p_stdout);
}
if (p_stderr) {
g_free(p_stderr);
}
if (p_error) {
g_error_free(p_error);
}
return 0;
}
Use g_spawn_async_with_pipes. Reading binary data from file descriptors is easy. If you really need to detect when the child exits, add a callback using g_child_watch_add or g_child_watch_add_full, but you can probably get away with just reading the descriptor until it returns an error.

How to reply a D-Bus message

I got the D-Bus server.c and client.c code, and made some modification.
I want the result that when type for example "hi" from client.c
server will print "receive message hi", and reply "reply_content!!!!!!" to client.c
But it seems that now client.c cannot get the reply message.
Anyone have the idea?
Thanks in advance.
"server.c"
/* server.c */
#include <dbus/dbus.h>
#include <stdbool.h>
#include <unistd.h>
#include <stdio.h>
#include <stdlib.h>
static DBusHandlerResult
filter_func(DBusConnection *connection, DBusMessage *message, void *usr_data)
{
DBusMessage *reply;
dbus_bool_t handled = false;
char *word = NULL;
DBusError dberr;
dbus_error_init(&dberr);
dbus_message_get_args(message, &dberr, DBUS_TYPE_STRING, &word, DBUS_TYPE_INVALID);
printf("receive message: %s\n", word);
handled = true;
reply = dbus_message_new_method_return(message);
char * reply_content = "reply_content!!!!!!";
dbus_message_append_args(reply, DBUS_TYPE_STRING, &reply_content, DBUS_TYPE_INVALID);
dbus_connection_send(connection, reply, NULL);
dbus_connection_flush(connection);
dbus_message_unref(reply);
return (handled ? DBUS_HANDLER_RESULT_HANDLED : DBUS_HANDLER_RESULT_NOT_YET_HANDLED);
}
int main(int argc, char *argv[])
{
DBusError dberr;
DBusConnection *dbconn;
dbus_error_init(&dberr);
dbconn = dbus_bus_get(DBUS_BUS_SESSION, &dberr);
if (!dbus_connection_add_filter(dbconn, filter_func, NULL, NULL)) {
return -1;
}
dbus_bus_add_match(dbconn, "type='signal',interface='client.signal.Type'", &dberr);
while(dbus_connection_read_write_dispatch(dbconn, -1)) {
/* loop */
}
return 0;
}
Here is client.c
#include <dbus/dbus.h>
#include <stdbool.h>
#include <unistd.h>
#include <stdio.h>
#include <stdlib.h>
static DBusHandlerResult
filter_func(DBusConnection *connection, DBusMessage *message, void *usr_data)
{
dbus_bool_t handled = false;
char *word = NULL;
DBusError dberr;
dbus_error_init(&dberr);
dbus_message_get_args(message, &dberr, DBUS_TYPE_STRING, &word, DBUS_TYPE_INVALID);
printf("receive message %s\n", word);
handled = true;
return (handled ? DBUS_HANDLER_RESULT_HANDLED : DBUS_HANDLER_RESULT_NOT_YET_HANDLED);
}
int db_send(DBusConnection *dbconn)
{
DBusMessage *dbmsg;
char *word = (char *)malloc(sizeof(char));
int i;
dbmsg = dbus_message_new_signal("/client/signal/Object", "client.signal.Type", "Test");
scanf("%s", word);
if (!dbus_message_append_args(dbmsg, DBUS_TYPE_STRING, &word, DBUS_TYPE_INVALID)) {
return -1;
}
if (!dbus_connection_send(dbconn, dbmsg, NULL)) {
return -1;
}
dbus_connection_flush(dbconn);
printf("send message %s\n", word);
dbus_message_unref(dbmsg);
return 0;
}
int main(int argc, char *argv[])
{
DBusError dberr;
DBusConnection *dbconn;
dbus_error_init(&dberr);
dbconn = dbus_bus_get(DBUS_BUS_SESSION, &dberr);
if (!dbus_connection_add_filter(dbconn, filter_func, NULL, NULL)) {
return -1;
}
db_send(dbconn);
while(dbus_connection_read_write_dispatch(dbconn, -1)) {
db_send(dbconn);
}
dbus_connection_unref(dbconn);
return 0;
}
You're communicating only with signals at the moment, which don't have a return value.
In client.c, use dbus_message_new_method_call instead of dbus_message_new_signal, and in server.c you probably have to change type='signal' to type='method_call'.

access webcam fail

i am still new on opencv, i make simple program based on sample to access webcam but always fails. i change variable id to 0,1,2...100 but i got same result. this is my program:
#include "cv.h"
#include "highgui.h"
#include "stdio.h"
#include "iostream"
// A Simple Camera Capture Framework
int main()
{
IplImage* img = NULL;
CvCapture* cap = NULL;
int id=0;
cap = cvCaptureFromCAM(id);
cvNamedWindow("Images",CV_WINDOW_AUTOSIZE);
if ( !cap )
printf("ERROR\n\n");
else
for(;;)
{
img = cvQueryFrame(cap);
cvShowImage("Imagenes", img);
cvWaitKey(10);
}
cvReleaseImage(&img);
cvReleaseCapture(&cap);
return 0;
}
thank you for your help
Do yourself a favor and check the return of the functions. Maybe some of them are failing and you'll never know why.
Another tip: try with id = -1.
#include <iostream>
#include <sstream>
#include <string>
#include <cv.h>
#include <highgui.h>
int main()
{
CvCapture* capture = NULL;
if ((capture = cvCaptureFromCAM(-1)) == NULL)
{
fprintf(stderr, "ERROR: capture is NULL \n");
return -1;
}
cvNamedWindow("mywindow", CV_WINDOW_AUTOSIZE);
cvQueryFrame(capture); // Sometimes needed to get correct data
IplImage* frame = NULL;
while (1)
{
if ((frame = cvQueryFrame(capture)) == NULL)
{
fprintf( stderr, "ERROR: cvQueryFrame failed\n");
break;
}
if (frame == NULL)
{
usleep(100000);
continue;
}
cvShowImage("mywindow", frame); // Do not release the frame!
int key = cvWaitKey(10);
if (key == 27) // ESC was pressed
break;
}
cvReleaseCapture(&capture);
cvDestroyWindow("mywindow");
return 0;
}

Resources