|
Len,
nothing to do with reentrancy issues during COM method calls.
I've got an interface marshalled between different threads and
the interface under certain circumstancies need to know which thread has been calling
to provide different services because this thread is not so safe to produce
good result using this method. The problem of marshalling an interface is that
during the method call the GetCurrentThreadId obviously return the marhsalled thread id
ciao
|
|
|
|
|
Anonymous_com wrote:
I've got an interface marshalled between different threads and
I'd do it differently
Len Holgate
www.jetbyte.com
The right code, right now.
|
|
|
|
|
do I have to pray you to know how ?
|
|
|
|
|
Anonymous_com wrote:
do I have to pray you to know how ?
No, but I need a little more information. So back to my original question. Why do you need to know the thread id. Or, more precisely, why do you need to act differently depending on the caller's thread. I guess I'm asking what the 'certain circumstances' are and why the "thread is not so safe to produce good result".
Once I know this, I can answer
Len Holgate
www.jetbyte.com
The right code, right now.
|
|
|
|
|
Len,
you're tech teaser (no offense)
well, you can imagine this scenario as a super marshal :
certain threads cannot perform some operation
on certain methods. This could be achieved splitting the interface
but at the moment it's impossible
|
|
|
|
|
Anonymous_com wrote:
well, you can imagine this scenario as a super marshal :
certain threads cannot perform some operation
on certain methods. This could be achieved splitting the interface
but at the moment it's impossible
What I find difficult to reconcile is the fact that the knowledge of when the operation can safely be called by a particular thread is being placed in the object, rather than in the thread. If the thread deals with this issue then your problem goes away. The ideal solution is splitting the interface as you say. If that's not possible then personally I'd prefer to put the code that decides if the call is allowable or not on the caller's side of the interface rather than on the object's side. Doing it the way you're doing at the moment is likely to come back and bite you at a later date
Not amazingly helpful advice I know but I usually find it's worth dealing with the pain of these kinds of problems straight away - ie refactor the interface and adjust the design - rather than patching in a quick fix and finding myself with strangeness occurring just as I'm about to ship the product.
This code from Dharma Shukla's CoHack pages might help.
Len Holgate
www.jetbyte.com
The right code, right now.
|
|
|
|
|
Is there any way to kill a COM Object which I have started.
Normally I create the COM Object, and when I'm done with it I call obj->Release(); to decrease the ref. count.
But what if the COM Object stops responding?
Is there anyway to kill it...
Something like: KillComObjectNow(obj);
I know I know, it might cause resourse/memory leaks and stuff, but...
The problem is that I'm writing a server-thing for which people can write plug-ins/extensions in COM, and if one of those stops responding I want to kill it...
- Anders
Money talks, but all mine ever says is "Goodbye!"
|
|
|
|
|
You can use MessageFilters, look at IMessageFilter
|
|
|
|
|
will not work in MTA.
soptest
|
|
|
|
|
Hi All,
I encountered the following problem:
I succeeded using an ocx file through one exe file, while didn't succeed doing it through another exe.
In Details:
I wrote an exe file, that addresses a dll. This dll consists of a dialog, on which I added an ActiveX component (as a control). This activeX component is an OCX file.
It all worked very well: I managed interacting with that ocx. Everything was perfect.
Now the problems begin:
I wrote another exe, which, using the same principle, addresses the dll (mentioned above). But the program crashed.
While debugging, I see the there's no problem getting from the exe to the DIALOG on that dll, but the program fails when trying to address the OCX on the dialog.
I also saw that the problem relates to the CONTAINING and WRAPPING of the ocx:
Two pointers: COleControlContainer* m_pCtrlCont, and COleControlSite* m_pCtrlSite have NULL value
(both members of class CWnd, in file afxwin.h).
What seems to be the problem? Why can't I address that ocx from the other application?
I work Visual C++ 6.0, Windows NT.
Thanks a lot.
|
|
|
|
|
|
Hi!
How do I do start, which method do I use if I want an already open Windows file Open/Save dialog to change path?
Thanks!
/Jii
|
|
|
|
|
Object A was configged as "Requer Transaction" property and Object B(Actually is a databass access object to oracle and use ado to access to the datasource) was configged as "Supported Transaction" one.now A will invoke B and B must run in the Transaction context.is that practical and how to write the implement code of enlist the two transaction? thank you.
Scratch
|
|
|
|
|
Hi, i appologise if this question has been asked be before but its got me stummped, i need to overwrite one of the function pointers in a COM interface, i dont have access to the COM source nor can i modify it, i simply need to overwrite the pointer, i keep getting access violations.??
Goes something like this.
IInterface * MyInterface= MakeInterface();
unsigned * vTbl = ((unsigned**)MyInterface)[0];
vTbl[THE_FUNCTION_INDEX] = NewFunction;
Hope that gives you the idea of what i want, kinda like hooking a COM interface, i have yet to find an easy/any soloution like simply overwriting the functions pointer.
|
|
|
|
|
Implement interface you want to overwright.
1. You can use ATL to implement Interface.
2. Or see this example:
#include "stdafx.h"
#include "windows.h"
#import "testObj.dll"
#include "comdef.h"
class MyNew: public ::TESTOBJLib::ItestPtr
{
public:
MyNew()
{
::CoInitialize(0);
::TESTOBJLib::ItestPtr p;
(*((::TESTOBJLib::ItestPtr*)this)).CreateInstance(L"TestObj.test");
}
~MyNew()
{
this->Release();
::CoUninitialize();
}
HRESULT In( _bstr_t wsIn )
{
(*((::TESTOBJLib::ItestPtr*)this))->In(wsIn);
return S_OK;
};
HRESULT f()
{
::OutputDebugString("this my function.");
return S_OK;
}
};
int main(int argc, char* argv[])
{
MyNew p;
p.f();
p.In("test");
return 0;
}
soptest
|
|
|
|
|
Ok forgive me, im not familiar "yet", with COM and ATL etc, but from what i can gather that would require implementing every method and making it call the base (default) method for all methods i want to keep, unfortunatly the interfaces are pretty big reaching into the hundreds of methods and implementing each method to call its base method would be very time consuming.
|
|
|
|
|
COM supports two kinds of object orientation over binary components with C++. They are Containment and Aggregation.
Containment: This is traditional C++ wrapping up style where the new CoClass will implement the desired interface and internally use the Binary component to perform the operations.
Aggregation: The new CoClass will delegate the implemented interafce requests to the binary component and any request to the CoClass from binary component will be delegated back. This is a kinda tricky thing and has got restrictions. Like, the component being aggregated should be an In-Proc Server and should support component aggregation.
Advantage of Containment Over Aggregation: It doesnt have any restrictions.
Advantage of Aggregation Over Containment: You dont have to implement all interface methods by youself in the component. You'll just delegate, this will be handy if interface has lot of methods.
Check out COM books for further details.
Thanks,
Ramu
|
|
|
|
|
You are probably German. I think only Germans use the word "overwrite" like this. In the past I have tried to explain that the correct English word probably is "override" but Germans insist they are correct and I am mistaken.
Perhaps you really want to override the function pointer, and if so then perhaps you will get help if you state the problem that way.
|
|
|
|
|
Hi All,
ATL forces the developer to implement the Call Factory (IClassFactory) and the Interface(s) implementation as part of the same C++ class (done through their template classes).
My question is: Is it possible to actually implement them (like in the old days) as seperate classes? This of course while using ATL. If so, what is the trick.
Any help is greatly appreciated.
Regards,
...Marc
marc.bednar@cactus.ca
|
|
|
|
|
Hi all,
I've been digging through tons of documentation but as of yet, I still haven't found an answer to a simple question.
When an MFC ActiveX control fires an event, does it return immediately or does it return only after the container's event handler is finished?
Thanks!
|
|
|
|
|
|
Im doing a simple non-MFC application.. I need to convert an ASCII string into an OLECHAR array. I want to pass my string into a SysAllocString(); function call like this:
<br />
char string[] = "ASCII STRING";<br />
(t+f)->str = SysAllocString(string);<br />
Of course this doesnt work because, SysAllocString is expecting an OLECHAR FAR*. The function works fine when I do:
<br />
(t+f)->str = SysAllocString(OLESTR("Test String"));<br />
Im actually passing in an array of UDTypes with variable length strings from VB and populating each element of the array / structure.
Im not very familiar with this whole ATL/COM string stuff.. =) Ill be honest, Im a C programmer, so Im out of my element. What can I do.. Please Help.
Ryan Baillargeon
Software Specialist
Fuel Cell Technologies Inc.
|
|
|
|
|
|
If you #include <atlbase.h> & <atlconv.h> , you can use the ATL string conversion macros. These convert strings 'on-the-fly':
const char* s;
BSTR s = ::SysAllocString(A2COLE(s));
LPCTSTR ts;
BSTR s = ::SysAllocString(T2COLE(ts));
They 'do the right' thing wrt conversion to/from Unicode & ASCII & use the stack for temporary string allocation (so are reasonably efficient and deallocate the temporaries automatically).
Alternatively, the CComBSTR or _bstr_t classes seem to work pretty well (I tend to use _bstr_t because it's got char* & wchar_t* extraction operators). The following code should properly allocate a BSTR for use in a C struct
struct {
....
BSTR bs;
....
} thing;
char* s;
thing.bs = CComBSTR(s).Detach();
Just remember to make sure that the BSTR is properly deallocated - using SysFreeString if you do it yourself. For this reason, you'd be better having a CComBSTR in your struct if that's at all practical, as the CComBSTR will deallocate the BSTR in it's destructor.
HTH
Stuart Dootson
'Java, Basic, who cares - it's all a bunch of tree-hugging hippy cr*p'
|
|
|
|
|
Just take care of the conversion macros like A2W, W2A, A2COLE, etc.. for 2 reasons:
1) They dynamically allocate memory ON THE STACK. This is good because it is fast and memory autmatically gets freed when the stack goes out of scope. However, there are memory limitations, so big strings could cause nasty things....
2) CComBSTR (or any other BSTR strings) support EMBEDDED NULLs. For those who do not know what embedded nulls are - basically, a BSTR could be: "Hello\0World" (notice the 0 in the middle.). When a BSTR is counted using SysStringLen(), the proper lenght is taken (SysAllocString stores the lenght of the string). However, if strlenW is used, it will stop after the "Hello" and not count the "World" part. A2W, W2A, A2COLE etc.. use strlenW to get the lenght of the string and not SysStringLen... this causes a converted string to be truncated when it encounters and embedded NULL.
Jeremy.
"Hey man, Taliban, Tali me Banana."
|
|
|
|