Results 1 to 15 of 15

Thread: how to init runtime of threadproc in activex dll without multiuse class creation-reg

  1. #1

    Thread Starter
    Hyperactive Member
    Join Date
    Apr 2015
    Posts
    356

    how to init runtime of threadproc in activex dll without multiuse class creation-reg

    Dear Trick,

    can you clarify how to init runtime of Threadproc in actx dll set to apartment threaded where the thread is created using CreateThread api in the actx dll without using multiuse class of dll with CreateObject thru vbdllgetclassobject.The standard exe just loads the actx dll thru project references.

    regards,
    JSVenu

  2. #2

  3. #3

    Thread Starter
    Hyperactive Member
    Join Date
    Apr 2015
    Posts
    356

    Re: how to init runtime of threadproc in activex dll without multiuse class creation-

    Quote Originally Posted by The trick View Post
    Please attach the example which causes the error.
    There is no reason to performing special initialization for an ActiveX-DLL because it's initialized automatically.
    Dear Trick,

    I made a simple project which is attached.
    The simple project consists of two projects in simpleproject folder which are
    1. stdexe project Displayaformofdllinnewthreadfromactivexd in stdexe folder.
    2. Actx dll project actxdllwithapt_threaded in actxdllaptthd folder.

    Just compile actxdllwithapt_threaded actx project and generate actxdllwithapt_threaded.dll
    Just include actxdllwithapt_threaded.dll in Displayaformofdllinnewthreadfromactivexd std exe project from project references in the IDE and compile to Displayaformofdllinnewthreadfromactivexd.exe.

    Now when we run Displayaformofdllinnewthreadfromactivexd.exe in compiled mode outside IDE it displays form of
    actx dll in new thread whenever we click on DisplayFormofAptThreadedactxDLL button of displayed form.

    In the following code

    Code:
    Public Function ThreadProc( _
        ByRef tData As tThreadData) As Long
        Dim cObj            As IUnknown
        Dim tempobj As Class1
        Dim frm As Form1
       
        
        Set cObj = CreateIExprSrvObj(0, 4, 0)
        
        CoInitialize ByVal 0&
        Set tempobj = CreateObject("actxdllwithapt_threaded.Class1")  'init runtime
        Set frm = New Form1
        frm.Show vbModal
        
        Set frm = Nothing
        
        CoUninitialize
        
        Set cObj = Nothing
        Set tempobj = Nothing
    End Function
    I am initializing runtime of ThreadProc use the following code:
    Set tempobj = CreateObject("actxdllwithapt_threaded.Class1") 'init runtime

    I donot want to use Class1 multiuse class for initializing runtime for this ThreadProc.
    Instead of the above line containing CreateObject using multiuse class class1 I want to use vbdllgetclassobject for initializing
    this actx dll ThreadProc for displaying the dll form in this ThreadProc in Apartment threaded mode since CreateObject internally calls vbdllgetclassobject in the cycle.

    I can solve the above example using vbdllgetclassobject by setting actx dll to single threaded.But I wanted to solve it using vbdllgetclassobject by setting actx dll to apt threaded since it is supposed to work since CreateObject internally calls vbdllgetclassobject. But it is not working in apt mode using vbdllgetclassobject explicitly.

    You can see that the ThreadProc in actx dll will not initialize automatically as you said.

    This is the sincere explanation with simple example I can give you Trick without any intention of hijacking any threads.

    regards,
    JSVenu
    Attached Files Attached Files

  4. #4
    PowerPoster
    Join Date
    Feb 2015
    Posts
    2,797

    Re: how to init runtime of threadproc in activex dll without multiuse class creation-

    Code:
    Public Function ThreadProc( _
                    ByVal lUnused As Long) As Long
        Dim cExprSrv    As IUnknown
        Dim cInitObj    As IUnknown
        Dim cForm       As Form1
        
        Set cExprSrv = CreateIExprSrvObj(0, 4, 0)
        
        CoInitialize ByVal 0&
        Set cInitObj = InitVbProjContext()
        Set cForm = New Form1
        cForm.Show vbModal
        Set cForm = Nothing
        Set cInitObj = Nothing
        
        CoUninitialize
    
    End Function
    
    Public Function InitVbProjContext() As IUnknown
        Dim pVBHeader       As Long
        Dim pCOMData        As Long
        Dim lOfstRegInfo    As Long
        Dim pRegInfo        As Long
        Dim pfn             As Long
        Dim hLib            As Long
        Dim iTypes(2)       As Integer
        Dim vParams(2)      As Variant
        Dim lList(2)        As Long
        Dim bIID(1)         As Currency
        Dim cFactory        As IUnknown
        Dim cObject         As IUnknown
        Dim hr              As Long
        Dim vRet            As Variant
        
        hLib = GetModuleHandle(StrPtr("actxdllwithapt_threaded.dll"))
        pfn = GetProcAddress(hLib, "DllGetClassObject")
        If pfn = 0 Then Exit Function
        
        ' // Get VBHeader
        GetMem4 ByVal pfn + 2, pVBHeader
        ' // Get COM data
        GetMem4 ByVal pVBHeader + &H54, pCOMData
        ' // Get Reg info
        GetMem4 ByVal pCOMData, lOfstRegInfo
        
        pRegInfo = pCOMData + lOfstRegInfo
    
        ' // IClassFactory
        bIID(0) = 0.0001@
        bIID(1) = 504403158265495.5712@
    
        hr = DllGetClassObject(ByVal pRegInfo + &H14, bIID(0), cFactory)
        
        If hr >= 0 And Not cFactory Is Nothing Then
            
            ' // Call IClassFactory::CreateInstance
    
            iTypes(0) = vbLong
            iTypes(1) = vbLong
            iTypes(2) = vbLong
    
            bIID(0) = 0
            
            vParams(0) = 0&
            vParams(1) = VarPtr(bIID(0))
            vParams(2) = VarPtr(cObject)
            
            lList(0) = VarPtr(vParams(0))
            lList(1) = VarPtr(vParams(1))
            lList(2) = VarPtr(vParams(2))
    
            hr = DispCallFunc(ByVal ObjPtr(cFactory), &HC, CC_STDCALL, vbLong, 3, iTypes(0), lList(0), vRet)
            
            If hr >= 0 And vRet >= 0 Then
    
                Set InitVbProjContext = cObject
    
            End If
            
        End If
    
    End Function
    You don't need this code so you already use the registry-dependent code when you create an instance in the EXE.

  5. #5

    Thread Starter
    Hyperactive Member
    Join Date
    Apr 2015
    Posts
    356

    Re: how to init runtime of threadproc in activex dll without multiuse class creation-

    Quote Originally Posted by The trick View Post
    Code:
    Public Function ThreadProc( _
                    ByVal lUnused As Long) As Long
        Dim cExprSrv    As IUnknown
        Dim cInitObj    As IUnknown
        Dim cForm       As Form1
        
        Set cExprSrv = CreateIExprSrvObj(0, 4, 0)
        
        CoInitialize ByVal 0&
        Set cInitObj = InitVbProjContext()
        Set cForm = New Form1
        cForm.Show vbModal
        Set cForm = Nothing
        Set cInitObj = Nothing
        
        CoUninitialize
    
    End Function
    
    Public Function InitVbProjContext() As IUnknown
        Dim pVBHeader       As Long
        Dim pCOMData        As Long
        Dim lOfstRegInfo    As Long
        Dim pRegInfo        As Long
        Dim pfn             As Long
        Dim hLib            As Long
        Dim iTypes(2)       As Integer
        Dim vParams(2)      As Variant
        Dim lList(2)        As Long
        Dim bIID(1)         As Currency
        Dim cFactory        As IUnknown
        Dim cObject         As IUnknown
        Dim hr              As Long
        Dim vRet            As Variant
        
        hLib = GetModuleHandle(StrPtr("actxdllwithapt_threaded.dll"))
        pfn = GetProcAddress(hLib, "DllGetClassObject")
        If pfn = 0 Then Exit Function
        
        ' // Get VBHeader
        GetMem4 ByVal pfn + 2, pVBHeader
        ' // Get COM data
        GetMem4 ByVal pVBHeader + &H54, pCOMData
        ' // Get Reg info
        GetMem4 ByVal pCOMData, lOfstRegInfo
        
        pRegInfo = pCOMData + lOfstRegInfo
    
        ' // IClassFactory
        bIID(0) = 0.0001@
        bIID(1) = 504403158265495.5712@
    
        hr = DllGetClassObject(ByVal pRegInfo + &H14, bIID(0), cFactory)
        
        If hr >= 0 And Not cFactory Is Nothing Then
            
            ' // Call IClassFactory::CreateInstance
    
            iTypes(0) = vbLong
            iTypes(1) = vbLong
            iTypes(2) = vbLong
    
            bIID(0) = 0
            
            vParams(0) = 0&
            vParams(1) = VarPtr(bIID(0))
            vParams(2) = VarPtr(cObject)
            
            lList(0) = VarPtr(vParams(0))
            lList(1) = VarPtr(vParams(1))
            lList(2) = VarPtr(vParams(2))
    
            hr = DispCallFunc(ByVal ObjPtr(cFactory), &HC, CC_STDCALL, vbLong, 3, iTypes(0), lList(0), vRet)
            
            If hr >= 0 And vRet >= 0 Then
    
                Set InitVbProjContext = cObject
    
            End If
            
        End If
    
    End Function
    You don't need this code so you already use the registry-dependent code when you create an instance in the EXE.
    Dear Trick,

    Thankyou for the reply.
    I modified the activex dll (activex dll project code attached) according to above code but when I run the standard exe by including the dll thru project settings it crashes.Please clarify.

    regards,
    JSVenu
    Attached Files Attached Files

  6. #6

  7. #7

    Thread Starter
    Hyperactive Member
    Join Date
    Apr 2015
    Posts
    356

    Re: how to init runtime of threadproc in activex dll without multiuse class creation-

    Quote Originally Posted by The trick View Post
    Update the library name according the dll name.
    Dear Trick,
    Now it works fine.
    But now the real problem came when I use vbdllgetclassobject .
    When I use it it crashes in Createvbheadercopy.
    I am attaching activex dll updated.It was my real problem.
    regards,
    JSVenu
    Attached Files Attached Files

  8. #8

  9. #9

    Thread Starter
    Hyperactive Member
    Join Date
    Apr 2015
    Posts
    356

    Re: how to init runtime of threadproc in activex dll without multiuse class creation-

    Quote Originally Posted by The trick View Post
    You shouldn't use such approach. You shouldn't create a VBHeader copy.
    Dear Trick,

    It we use same vbheader then how to make sure that global variables are not cleared without using CreateVBHeaderCopy.
    Same is my problem in ExeFormCreator project which I asked in the link
    http://www.vbforums.com/showthread.p...multithreading #25.
    Please clarify.

    regards,
    JSVenu

  10. #10

  11. #11

    Thread Starter
    Hyperactive Member
    Join Date
    Apr 2015
    Posts
    356

    Re: how to init runtime of threadproc in activex dll without multiuse class creation-

    Quote Originally Posted by The trick View Post
    I already gave the code to make a NativeDLL from StdEXE.
    Dear Trick,

    Still I did not understand why CreateVBHeaderCopy fails in apartment threaded activex dll but works
    1. in a standard exe even when the main thread vbheader is changed to apartment model.
    2. in a activex dll set to single threaded model.

    Has this something to do with global variables .Please clarify.

    regards,
    JSVenu

  12. #12
    PowerPoster Arnoutdv's Avatar
    Join Date
    Oct 2013
    Posts
    6,734

    Re: how to init runtime of threadproc in activex dll without multiuse class creation-

    There are dozen of threads dealing with Multi Threading in VB6, all with a lot of complete code samples by The Trick and Schmidt.
    Which also causes a lot of friction between them, because it seems they both have a strongly developed different opinion how thing should work.
    But in all these threads you always need something different, which somehow is not dealt with in the given samples.

    It seems you need something so special that:
    a. it can not be done in VB6
    b. it's only a hypothetical use case
    c. you are trolling
    d. all of the above

    So what kind of application are you creating, because keep saying "just to study" is not a legitimate answer anymore
    Please clarify!

  13. #13

    Thread Starter
    Hyperactive Member
    Join Date
    Apr 2015
    Posts
    356

    Re: how to init runtime of threadproc in activex dll without multiuse class creation-

    Dear Arnoutdv,

    First let me thankyou for treating me asking something different but they are related to COM threading in a vc++ 6.0 unmanaged way. Actually I always think of COM threading to be understood in the same way as win32 unmanaged programming since I think in win32 way of unmanaged programming in vc++ 6.0.Now anyway I work in .NET where programming is made very easy.Long back when I worked in vb6.0 I maximum took support of vc++ 6.0 for advanced features like threading not available in vb6 at that time.I can tell you this type of interest makes me think and do some examples and ask the members since I really enjoy the subject from the solid examples provided by solid people.May be my thinking and doing like this help me in whatever language and platform I work in future in right direction.I am not developing any product and do not want to be idle.
    This is the sincere explanation I can give you.

    regards,
    JSVenu

  14. #14
    PowerPoster
    Join Date
    Feb 2015
    Posts
    2,797

    Re: how to init runtime of threadproc in activex dll without multiuse class creation-

    You shouldn't use the Apartment threading if you want to use shared memory because the compiler makes the apartment-aware code. Why do you need to use the Apartment threading mode if you want to use the shared variables? It exists exactly to isolate the global variables. You can't use shared variables in projects excluding the StdEXE one. (I don't consider the hacks like interception __vbaAptOffset etc.) Therefore it doesn't work in your cases.

    Moreover you shouldn't use an ActiveX-DLL in such scenario (sharing variables) because you can't ensure the context initialization control even if you use the single-threaded option. Imagine you create an object from such AxDLL - it uses the initial project context:


    , so all your global/static variables will be cleared when this object is being released:


    So you need to use the modified copy of the project-vb-header which contains exactly 0 such variables. The project i sent earlier (NativeDLL) does exactly that but you should control the lifetime of all the variables like in C/C++. All the variables are shared like in such languages.

    So if you want coding in more low-level you should be more responsible.

  15. #15

    Thread Starter
    Hyperactive Member
    Join Date
    Apr 2015
    Posts
    356

    Re: how to init runtime of threadproc in activex dll without multiuse class creation-

    Quote Originally Posted by The trick View Post
    You shouldn't use the Apartment threading if you want to use shared memory because the compiler makes the apartment-aware code. Why do you need to use the Apartment threading mode if you want to use the shared variables? It exists exactly to isolate the global variables. You can't use shared variables in projects excluding the StdEXE one. (I don't consider the hacks like interception __vbaAptOffset etc.) Therefore it doesn't work in your cases.

    Moreover you shouldn't use an ActiveX-DLL in such scenario (sharing variables) because you can't ensure the context initialization control even if you use the single-threaded option. Imagine you create an object from such AxDLL - it uses the initial project context:


    , so all your global/static variables will be cleared when this object is being released:


    So you need to use the modified copy of the project-vb-header which contains exactly 0 such variables. The project i sent earlier (NativeDLL) does exactly that but you should control the lifetime of all the variables like in C/C++. All the variables are shared like in such languages.

    So if you want coding in more low-level you should be more responsible.
    Dear Trick,

    Thankyou very much for your awesome support and solid explanation which I understood upto some extent and will try to understand well and I am grateful to you for the help extended.

    regards,
    JSVenu

Posting Permissions

  • You may not post new threads
  • You may not post replies
  • You may not post attachments
  • You may not edit your posts
  •  



Click Here to Expand Forum to Full Width