Search Unity

Sockets in Native Plugin

Discussion in 'Multiplayer' started by ChristineRuss, May 11, 2018.

  1. ChristineRuss

    ChristineRuss

    Joined:
    May 11, 2018
    Posts:
    5
    Hi,

    I am trying to use sockets in C++ code to connect to a host in a native plugin in Unity on Windows 10. Looking at the traffic in rawcap, I do not see any packets that access the port I am using.

    When I connect to the same host from a Windows native executable, I see the port I am trying to access. Basically my access is not getting out of my Unity process. Please note, I have checked/tried changing all applicable firewall settings.

    Should it be possible to do something like this? All I have read seems to indicate that I should be using Unity's networking API's.

    Best regards,
    Christine
     
  2. newjerseyrunner

    newjerseyrunner

    Joined:
    Jul 20, 2017
    Posts:
    966
    I'm confused, can you post a flowchart? Sockets are sockets, it doesn't matter if you're using C#, C++ or hell PHP, they're all using winsock underneath.

    Let me make sure I understand. You wrote a plugin for Unity using C++. In the C++, you use winsock as a tcp client to talk to a server which is a tcp listener. You know that the server already works because you can connect to it with another C++ program that you wrote. The server is also written in C++ and is listening and bound correctly. That other C++ program that you wrote, does it share the codebase with the plugin that you made? ie, are you certain that the client code is exactly the same. Sockets are finicky, everything has to be set up just right, something as dumb as changing a 127.0.0.1 to a localhost can affect behavior.

    Every winsock command will return an error code. Do you log these error codes both client and server side? I'm betting somewhere one of the functions ($1 bet on getaddrinfo) is returning an error. Also, are you sure you've called WSAStartup()? That's easy to forget in a module. Did you #define WIN32_LEAN_AND_MEAN in one place and not the other?
     
  3. ChristineRuss

    ChristineRuss

    Joined:
    May 11, 2018
    Posts:
    5
    Hi newjerseyrunner,

    First, thank you for your reply.

    Yes, you understand correctly about what I am doing. One additional detail is that the other C++ program I wrote is a simple Windows console program that links to/uses the same native plugin DLL that I am trying to use in Unity. I don't do any extra setup in the console program.

    So, the connection code is the same because it is in the DLL. When I link the DLL to the native console program, I can see packets coming out to the desired destination port. When I link the DLL into Unity as a plugin, I do not see my packets coming out.

    I will log some more errors.

    I also encountered this same kind of issue when trying to do qjsonrpc in a native plugin in Unity.
     
  4. newjerseyrunner

    newjerseyrunner

    Joined:
    Jul 20, 2017
    Posts:
    966
    Have you used DependencyWalker to make sure that the DLL that you think it's loading is really the one that's being loaded? Remember that Unity builds to different directories depending on it's project settings, so it may be loading another copy that you have somewhere.

    Another possibility is that the Unity app has already called WSAStartup and I believe that calling it twice may be problematic.
     
    ChristineRuss likes this.
  5. ChristineRuss

    ChristineRuss

    Joined:
    May 11, 2018
    Posts:
    5
    I put the all of the required dependencies (with the exception of runtime libraries) in the same directory underneath my Assets folder in my Unity project to eliminate questions about what is being loaded from where.

    In the console program, I explicitly set the environment to that same directory (underneath Assets) to make sure I am loading the same things that Unity does. I am able to verify that the DLL's that are being loaded in the console program (via the Output window, Visual Studio 2017) are the ones located in the Assets directory.

    The actual connection call (inside the plugin DLL) that I am doing is a third party client connecting to a third party server. It is a wrap of an actual socket connect to host call. I can try the low level winsock version and see if I have the same issue.
     
  6. ChristineRuss

    ChristineRuss

    Joined:
    May 11, 2018
    Posts:
    5
    Hi newjerseyrunner,

    I just got some basic winsock code to connect from the native plugin in Unity! I suspect it could be one of the things you suggested (define WIN32_LEAN_AND_MEAN or WSAStartup) because I did both of them and things worked. Thank you for your help!
     
    newjerseyrunner likes this.
  7. ChristineRuss

    ChristineRuss

    Joined:
    May 11, 2018
    Posts:
    5
    Hi newjerseyrunner,

    I have some further information. After getting basic winsock stuff to work, I now have the third party client/server working from the Unity plugin. The problem was a missing dynamically loaded dependency (via LoadLibrary, no prepended path). Since my Unity exe is in a different directory than my plugins, and the plugins directory was not in my path, the library was not found. (I did not have this problem in the console app because I explicitly set the environment to the plugins directory) I found this with Dependency Walker (depends.exe, something you suggested). I had tried Dependency Walker with my plugin before I posted, but I did not think to use Dependency Walker to profile a running executable. I did this, and I found the missing LoadLibrary dependency. Unfortunately the error in Unity was just a failure of the API containing the LoadLibrary call which is why I did not immediately suspect another missing dependency. Thanks again for your help!
     
    newjerseyrunner likes this.