Announcement

Collapse
No announcement yet.

Interfaces

Collapse
X
 
  • Filter
  • Time
  • Show
Clear All
new posts

  • Interfaces

    Hi all,

    just having my first real crack at bashing out some code with PB Win 9.01 involving linking with a 3rd party OOP dll. All is going well so far in that I am just familiarising myself with the basic syntax of PB Win etc. and have managed to call some functions in some simple dlls I created specifically for my testing (the dll's have not been created in PB Win though purely because the huge OOP dll I eventually wish to link with has been coded in a different language).

    Must say, this is one cool language; especially with the addition of all the OOP stuff. Things have changed somewhat since the last time I looked! Very nice.

    Back to the question in hand. The dll in question returns, when requested, various interface pointers (not COM objects though). These interfaces do not inherit from iUnknown or iDispatch etc. but are kind of 'free standing'.

    Is this going to be a problem for PB Win? What I mean is, must all interfaces used in Powerbasic inherit from some pre-existing base class such as iUnknown etc? If so, then well, I can alter the dll in question to do that, but I would rather not if this could be avoided!

    Thanks for any replies.

    Stephen.
    http://www.arctic-reports.com/
    http://www.nxsoftware.com

  • #2
    Is this going to be a problem for PB Win? What I mean is, must all interfaces used in Powerbasic inherit from some pre-existing base class such as iUnknown etc?
    Yes. They are COM classes, not C++ classes.
    Forum: http://www.jose.it-berater.org/smfforum/index.php

    Comment


    • #3
      Hi Jose,

      thanks for the reply. I kind of suspected that this was the case.

      I will have to modify the dll then so that all interfaces inherit from iUnknown. That is not a problem.
      http://www.arctic-reports.com/
      http://www.nxsoftware.com

      Comment


      • #4
        Boy I like this language! Very nice.

        I have another question, however. A simple one.

        In my most recent test, I created a simple OOP dll (not in PowerBasic and not a COM dll). A function is exported which returns an interface pointer etc.

        No problem. The following Powerbasic code is linking with the dll, calling the exported function to obtain an interface pointer and is calling the interface methods without a problem.

        Code:
        #COMPILE EXE
        #DIM ALL
        
        INTERFACE testInterface
          INHERIT IUNKNOWN
          METHOD Test(BYVAL a AS STRING)
        END INTERFACE
        
        
        DECLARE FUNCTION CreateObject LIB "dll2.DLL" ALIAS "CreateObject" () AS testInterface
        
        
        FUNCTION PBMAIN () AS LONG
            DIM myObject AS testInterface
            LET myObject = CreateObject()
            myObject.Test("Hello there!")
        END FUNCTION
        My dumb-*** question : in the declare statement, I declare the function as returning a value of type 'testInterface'. Can I somehow replace this with one of Powerbasic's native types; e.g. DWORD? When I try this I get a type mismatch kind of error when I attempt to invoke the method later on.

        This will of course not add anything to the code, just to my understanding of Powerbasic etc. in wondering how to effectively recast variables etc?

        Thanks.
        http://www.arctic-reports.com/
        http://www.nxsoftware.com

        Comment


        • #5
          When I try this I get a type mismatch kind of error when I attempt to invoke the method later on.
          At compile time? Then you have a mismatch between your procedure header, or property/method definition or DECLARE statements for same and the CALL syntax; or you have not used the correct point-of-call parameter override. Code not shown. Error message not shown.

          To get your program to compile, all references to a procedure, method or property must be consistent with each other.

          For your program to work correctly, all references to a procedure, method or property must be defined consistent with the library.

          MCM
          Michael Mattias
          Tal Systems (retired)
          Port Washington WI USA
          [email protected]
          http://www.talsystems.com

          Comment


          • #6
            I could help you make this work with some additional code but do note that PB offers loading from dll without the need of registering the dll(!)
            This means you provide tlb data in resource or file and use that to load the dll but specific calls to skip registry stuff.
            hellobasic

            Comment


            • #7
              No, the code as listed above compiles fine and indeed works fine. The dll is not registered because it is not a COM server and I have no wish to take that route in this case.

              What I was just wondering is if it is possible to alter the Declare statement so that the function returns a native PowerBasic data-type, e.g. a DWORD. Is there then a way of casting this double word later on so that I can make use of the interface pointer?

              If not, no worries because the code is working fine.

              Thanks.
              http://www.arctic-reports.com/
              http://www.nxsoftware.com

              Comment


              • #8
                You can change the DECLARE all you want, but it won't change what the call returns.

                Eg You could write a standard windows program using PowerBASIC in which you DELCLARE or DIM variables for window handles as SINGLE variables and your program would work just fine, because thirty-two bits is thirty-two bits and you never do math on those handles.

                MCM
                Michael Mattias
                Tal Systems (retired)
                Port Washington WI USA
                [email protected]
                http://www.talsystems.com

                Comment


                • #9
                  Aye, but when I alter the declare to DWORD, the code then fails to compile because of the LET myObject = CreateObject() statement which is subsequently attempting to assign a DWORD to an object.

                  Guess what I am asking in this case is if there is a way of subsequently casting a DWORD to an object pointer? It is purely to complete my understanding.
                  http://www.arctic-reports.com/
                  http://www.nxsoftware.com

                  Comment


                  • #10
                    >which is subsequently attempting to assign a DWORD to an object.

                    You can't do that.

                    If what CreateObject() returns is actually some 32-bit entity, I would think you should be able to use a LONG or DWORD (or SINGLE!) variable here.

                    What I don't know is if .....
                    Code:
                      DELCARE            ..... AS DWORD 
                    
                      LOCAL pObj  AS   MyInterface PTR 
                      LOCAL obj    AS   MyInterface 
                    
                      pObj = CreateObject() 
                      obj = @pObj
                       
                      obj.Method  (params...)
                    ... will work.

                    MCM
                    Michael Mattias
                    Tal Systems (retired)
                    Port Washington WI USA
                    [email protected]
                    http://www.talsystems.com

                    Comment


                    • #11
                      Nearly!

                      Had to change the pointer to a DWORD PTR but then the compiler complains at the line obj = @pObj - type mismatch etc.

                      Oh well, perhaps we cannot cast in this manner?

                      Thanks anyhow.
                      http://www.arctic-reports.com/
                      http://www.nxsoftware.com

                      Comment


                      • #12
                        If what do you want is not to use AS testInterface, then you can use AS IUnknown or AS IDispatch.

                        You could use also AS DWORD, but then you will have to use pointers to stuff the content od the DWORD variable into the object variable and then call the AddRef method to increment the reference count.
                        Forum: http://www.jose.it-berater.org/smfforum/index.php

                        Comment


                        • #13
                          This is apparently what do you want to do:

                          Code:
                             LOCAL pObj AS DWORD
                             LOCAL obj AS MyInterface
                          
                             pObj = CreateObject()
                             POKE DWORD, VARPTR(obj), pObj
                             IF ISOBJECT obj THEN obj.AddRef
                          But this is a solution to be used only when you don't have an alternative, because if you poke around without concern of reference counting, GPFs or odd behavior are guaranteed.

                          Much easier to use AS InterfaceName, AS IUnknown or AS IDispatch.
                          Forum: http://www.jose.it-berater.org/smfforum/index.php

                          Comment


                          • #14
                            Aha, nice and that pointed the way to doing this via pointers without using an aditional call to the POKE function :

                            Code:
                            #COMPILE EXE
                            #DIM ALL
                            
                            INTERFACE testInterface
                              INHERIT IUNKNOWN
                              METHOD Test(BYVAL a AS STRING)
                            END INTERFACE
                            
                            
                            DECLARE FUNCTION CreateObject LIB "dll2.DLL" ALIAS "CreateObject" () AS DWORD
                            
                            
                            FUNCTION PBMAIN () AS LONG
                                DIM obj AS testInterface, ptr1 AS DWORD PTR
                                ptr1 = VARPTR(obj)
                                @ptr1 = CreateObject()
                                obj.Test("Hello there!")
                            END FUNCTION
                            Thanks, I like that.

                            The reference counting is not actually implemented in this dll (there is no need for it in this case) and so I have just substituted dummy methods for the 3 iUnknown methods.

                            Can I ask what the difference is between DIM and LOCAL when used in a sub or function etc? Are they interchangeable?

                            Thanks.
                            http://www.arctic-reports.com/
                            http://www.nxsoftware.com

                            Comment


                            • #15
                              DIM can be used to declare variables as well as dimension arrays. DIM defaults to a scope of LOCAL, meaning the variable only exists in the procedure that the DIM appears in. You can specify the scope of a variable using the DIM statement by adding the word LOCAL, STATIC, GLOBAL or THREADED between the AS and the data type (ie. DIM obj AS GLOBAL testInterface).

                              Personally, I only use DIM for dimensioning arrays (ie. DIM sNames(1 TO 100)) and using the LOCAL, STATIC, GLOBAL and THREADED statements to declare variables.
                              Jeff Blakeney

                              Comment


                              • #16
                                Originally posted by Jeff Blakeney View Post
                                Personally, I only use DIM for dimensioning arrays (ie. DIM sNames(1 TO 100)) and using the LOCAL, STATIC, GLOBAL and THREADED statements to declare variables.
                                Sounds like good advice to me. I shall do likewise from now on.

                                Thanks Jeff.
                                http://www.arctic-reports.com/
                                http://www.nxsoftware.com

                                Comment

                                Working...
                                X