Timeout and retry to secure real controllers discovery with PC SDK

labulabu France ✭✭
Dear All,

We are long time users of PC SDK and are facing increasing difficulties to secure the initial controllers discovery. I am feeling that our way of scanning for the controllers is "old fashion" and might be the cause for our troubles.

Is anybody experiencing such issues (controllers not discovered and needing several retries, long delays, ...)

Workarounds, code samples for this initial discovery xwarmly welcomed.

Thanks in advance to the community.

Comments

  • msalminenmsalminen Finland ✭✭
    Hi, 
    Yes this have been a problem for years (allways) also for me. The scan don't allways find the controllers well. Very frustrated.
    In couple of last projects I have try to connect anyway if I know the controller before by using its id. something like following code (still working on this)
     Guid gid = new Guid(id);
     netScanner.TryFind(gid, 1000, 2, out info);

    However I haven't yet made good pattern for this. I have some issues with timing to do this as I call scan in class constructor and I don't have the controller id's yet. I have to make timer etc.
    If somebodyhave ideas for this problem I am interested as well to hear them.

    Mika

  • labulabu France ✭✭
    Are we only 2 to have this issue?
  • bgrantbgrant Canada
    I also have this issue.
    My PC SDK application seems to find the specified controller by GUID very quickly if I have RobotStudio running and the controller is listed in the 'Recent Controllers' sections. There is some correlation there, I just have no Idea what the problem is. 
    If RobotStudio is not running, my PC SDK application will fail while trying to find the controller. 

    Any help on this would be greatly appreciated!
  • Maxim RiabichevMaxim Riabichev Sweden admin
    Hello,

    We've initiated troubleshooting for this issue.

    A collegue of mine will soon post a proposed workaround in the meanwhile.

    Maxim Riabichev
    PC Software Support Engineer
  • AdamSGAdamSG Sweden admin
    edited August 8
    Hello!

    I have taken a look at the issue of controllers not being discovered correctly.

    The reason it behaves this way is because the discovery of controllers is not really managed by the PC SDK application you are writing, but instead by a service called RobNetScanHost.exe. This service is started whenever you Scan using a NetworkScanner for example. It takes a while for this service to actually discover and get information from all controllers on the network.

    RobotStudio also uses this service, meaning that if you have had RobotStudio running for a while beforehand, the service will already have been running for a while.

    One quite simple way to work around this is by calling NetworkScanner.Scan() and then wait for a few seconds using a Stopwatch or by Sleeping the Thread. You can then call Scan again and get more discovered controllers.

    Another way to deal with it is by knowing which controllers you actually are looking for. As you discussed before, this can be done using Guids. If you take your time and let the scan find all controllers on the network you are interested in, you can then save the Guid of these controllers in a text file for example. This text file can then be read by a program and used with NetworkScanner.TryFind().

    I have attached a Visual Studio Project file with a simple example of how this can be implemented. It has worked well on our system and managed to find all our controllers consistently and quickly even after just having rebooted my computer (meaning that the service hasn't had a lot of time to look for controllers).

    Simply run SaveControllers() and then LoadControllers().

    Below is also the raw code:



    using System;
    using System.Collections.Generic;
    using System.IO;
    using System.Linq;
    using ABB.Robotics.Controllers;
    using ABB.Robotics.Controllers.Discovery;

    namespace GuidControllerScan
    {
        class Program
        {
            private static readonly int WAIT_TIME = 1000;
            private static readonly int RETRIES = 2;
            private static readonly string PATH_GUID = "C:\\TestGuid\\guid.txt";

            static void Main(string[] args)
            {
                //SaveControllers();
                LoadControllers();
                Console.ReadKey();
            }

            // Save the scanned controllers to the Guid file
            public static void SaveControllers()
            {
                ControllerInfo[] cInf = ScanControllerInfo();
                Guid[] guid = cInf.Select(e => new Guid(e.SystemId.ToString())).ToArray();
                WriteGuidLog(guid, PATH_GUID);
            }

            // Load the controllers from the saved Guid file
            public static void LoadControllers()
            {
                Guid[] guid = ReadGuidLog(PATH_GUID);
                ControllerInfo[] cInf = GetControllers(guid);
            }

            /// Attempts to get the controllers from an array of Guid
            public static ControllerInfo[] GetControllers(Guid[] guidArray)
            {
                Console.WriteLine($"Scanning for {guidArray.Length} Guid...");
                NetworkScanner networkScanner = new NetworkScanner();

                List<ControllerInfo> controllerInfoList = new List<ControllerInfo>();

                for (int i = 0; i < guidArray.Length; i++)
                    if (networkScanner.TryFind(guidArray[i], WAIT_TIME, RETRIES, out ControllerInfo info))
                        controllerInfoList.Add(info);

                Console.WriteLine($"Found {controllerInfoList.Count} ControllerInfo.");

                return controllerInfoList.ToArray();
            }

            /// Save the Guid as a text file
            private static void WriteGuidLog(Guid[] guidArray, string filePath)
            {
                Console.WriteLine($"Writing Guid log {filePath}");
                FileInfo info = new FileInfo(filePath);
                if (info.Exists)
                    info.Delete();
                else
                    info.Directory.Create();
                File.WriteAllLines(filePath, guidArray.Select(e => e.ToString()).ToArray());
                Console.WriteLine($"Finished writing Guid log {filePath}");
            }

            /// Read Guid from a text file
            private static Guid[] ReadGuidLog(string filePath)
            {
                Console.WriteLine($"Reading Guid log {filePath}");
                return File.ReadAllLines(filePath).Select(e => new Guid(e)).ToArray();
            }

            /// Scan the network for controllers
            private static ControllerInfo[] ScanControllerInfo()
            {
                Console.WriteLine($"Scanning for controllers...");
                NetworkScanner scanner = new NetworkScanner();
                scanner.Scan();
                // Wait a while for the scan to find more controllers if needed.
                System.Threading.Thread.Sleep(4000);
                scanner.Scan();
                Console.WriteLine($"Found {scanner.GetControllers().Length} controllers.");
                return scanner.GetControllers();
            }
        }
    }
    Post edited by AdamSG on

    Adam Gustavsson
    PC Software Support Engineer
  • bgrantbgrant Canada
    edited August 9
    Hi Adam,

    Thank you very much for the reply! I tried the code that you attached above and had the same result. The application will not find any controllers unless they are listed in the 'recent controllers' section of RobotStudio and RobotStudio is running. I did some investigation into the RobNetScanHost service and this is what I found: With RobotStudio running, the following ports are opened:


    Without RobotStudio running, there are no ports open. However, the RobNetScanHost service is started when the PC SDK application is launced. 



    Is RobotStudio passing in parameters to RobNetScanHost? RobNetScanHost seems to respond differently depending on which application starts it. 

    I look forward to your reply. 
  • bgrantbgrant Canada
    Hi Adam,

    Another thing I have found is that once I add a controller into RobotStudio, the RobComCtrlServer consumes the following port:


  • AdamSGAdamSG Sweden admin
    Hello again,

    I tried the same thing as you did and looked at netstat after restarting my computer and starting my PC SDK application right away. I did however find that the service was actually using the right ports from the start without having to start RobotStudio! (see image)



    I wonder if there are any differences in our systems and RobotStudio versions. I am running Windows 10 with RobotStudio 6.07.01. The version of
    C:\Program Files (x86)\Common Files\ABB Industrial IT\Robotics IT\RobAPI\RobNetScanHost.exe for me is 6.7.1011.1 (see image). Is there any difference on your system?



    Adam Gustavsson
    PC Software Support Engineer
  • bgrantbgrant Canada
    Hi Adam,

    There is a difference in our systems. I am running Windows 7. 





    I am going to remove all of the software and reinstall it. I will report back with the results. 
  • AdamSGAdamSG Sweden admin
    I just checked with my colleague who is running windows 7 on his computer and it worked fine there as well... I will await your re-installation meanwhile. We are also leaving for the weekend so I will give it some more thinking until then,

    Adam Gustavsson
    PC Software Support Engineer
  • bgrantbgrant Canada
    Hey Adam,

    I am starting to believe this is a windows firewall problem associated with with my VPN. I assume that the firewall is allowing traffic when RobotStudio is open but blocking the ports when RobotStudio is closed. 

    I uninstalled and reinstalled everything but had the same result. 
  • bgrantbgrant Canada
    Hi Adam,

    I have been able to get my application to work. I believe there were two steps that fixed the problem.

    The first step was to setup ports 5512 thru 5515 in the firewall (outlined in this document http://developercenter.robotstudio.com/BlobProxy/manuals/RobotStudioOpManual/doc76.html).
    Although RobNetScanHost was allowed through the firewall, adding the ports seemed to help. 

    The second step was to add the remote controllers to the App.config file. 

     <remoteControllers>
          <controller id="192.168.10.11" />
          <controller id="192.168.10.12" />
          <controller id="192.168.10.21" />
          <controller id="192.168.10.22" />
          <controller id="192.168.10.23" />
          <controller id="192.168.10.24" />
          <controller id="192.168.10.31" />
          <controller id="192.168.10.32" />
          <controller id="192.168.10.33" />
          <controller id="192.168.10.34" />
          <controller id="192.168.10.41" />
          <controller id="192.168.10.42" />
          <controller id="192.168.10.43" />
          <controller id="192.168.10.44" />
          <controller id="192.168.10.51" />
          <controller id="192.168.10.52" />
          <controller id="192.168.10.53" />
          <controller id="192.168.10.54" />
        </remoteControllers> 

    I hope this information will prove useful to other users. 
  • AdamSGAdamSG Sweden admin
    Glad you got it to work!

    Adam Gustavsson
    PC Software Support Engineer
Sign In or Register to comment.