Home AMX User Forum NetLinx Studio

Multiple System Communication

Greetings,

I need a memory refresher on communicating amongst multiple systems. We did this in programmer II class, but I never really had an opportunity to do it until now.

I have a Netlinx system at my office which needs to change variables on several systems installed in the field. All systems involved have Internet access with the appropriate ports forwarded.

Could someone please help get me started?

Thank you.

Comments

  • Reese JacobsReese Jacobs Posts: 347
    Multiple System Communication

    Some basics:

    - All of the systems involved need to have unique System Numbers

    - You will need to add a URL entry using Netlinx Studio to the Office Master for each of the field systems you wish to connect and control (you do not need nor want URL entries in the Field system Masters)

    - Alternatively, you could programmatically add the URL entries to the Office system Master using ADD_URL_ENTRY() calls [I generally do this in my Netlinx code in DEFINE_START in case the Master is ever replaced and I forget to add the URL back using Studio].


    Once the URL entry is established in your Office master for any of the Field masters, you can communicate between the systems in a variety of ways. You can generate CHANNEL events to the other system using ON/OFF/TO/PULSE, generate BUTTON events using DO_PUSH, send levels to create LEVEL events, send strings or commands to the other system using SEND_STRING or SEND_COMMAND to a device, or any combination of these. The only thing you need to remember is that devices on the remote systems must be qualified with the system number of that system. For instance, if your Office master is system 1 and one of the Field masters is system 2, then the following could be used to send a command to a virtual device on the Field master:
    vdvOffice = 33000:1:0            // Virtual device on this Master for comparison
    vdvField1 = 33000:1:2            // Virtual device on the Field master
    
    // Send a command from the Office to the Field1 master
    
    SEND_COMMAND vdvField1,"'command data to set a variable'"
    

    On the Field system, you could then do the following:
    vdvField1 = 33000:1:0            // this is vdvField1 referenced from Office master
    
    // Handle a command string from the Office system
    
    DATA_EVENT[vdvField1]
    {
      COMMAND:
      {
        Handle the commands from the Office system
      }
    }
    

    There are many ways to do this but you get the idea. Button and Channel events are very convenient ways to communicate between remote systems. You can develop your own control protocol for exchanging data and then use Data events along with Commands/Strings to communicate.

    If the system numbers are not unique or for some reason connecting the Masters via URL lists is not desired, since all of the systems are accessible on the network, you could implement your control protocol over TCP and use IP_CLIENT_OPEN from the Office system to connect to the Field masters. The Field masters would have to provide a TCP server interface using IP_SERVER_OPEN. This technique is considerably more difficult to master since it involves Data events on the client and server to detect connections being made and lost and then Strings need to be sent back and forth across the socket connection once the systems are connected. However, it is an alternative to connecting Masters through URL lists and one that is generally not discussed in any great detail in programming classes.

    I have used both techniques depending on the situation. Letting Netlinx handle Master connections through the URL list is considerably easier to implement and you should find there are several easy ways to implement communication among the systems using Channels, Buttons, or Strings to accomplish what you want to do. I know that several other forum members use Master to Master a great deal as well and perhaps they can share some ideas and techniques. The Netlinx Programming Guide does have a pretty good section on Master to Master - you might check that out as well.

    Reese
  • DHawthorneDHawthorne Posts: 4,584
    This reminds me of an odd situation I have not quite been able to fully figure out, and it must somehow touch upon how virtual devices are managed internally in a NetLinx master.

    I have a multi-master system that runs a multiroom audio system on the central master that is driven by an AS-16 audio switch. There are two local systems in the house with their own masters that treat the multiroom audio system itself as one of thier sources. Since the AS-16 module uses a virtual device as it's control interface, I defined that same virtual on all the masters so they could access the multiroom states and control it. Levels and channels update perfectly this way and present no problem. However, I cannot get a SEND_COMMAND to this virtual to work on a master that it is not native to. Oddly enough, if I create another virtual and define it on both systems, I can pass SEND_COMMANDS to that and they get through. It would seem that you can send a command to a virtual only if it is native to the master from which the SEND_COMMAND originates. You can receive them just fine with a data event across masters, just not send them. I haven't been able to pursue this any further than that, nor check if it applies to SEND_STRING as well as SEND_COMMAND.

    To clarify, let's say I have two systems. I define my virtual control for the audio switch as 33001:1:1 on both masters. From master 1, SEND_COMMANDs to that virtual are received and acted on, but if I send the same command from master 2, they are not. Channel pushes and level events cross over without issue (I think...now that I am thinking about it, they might only be going in one direction too, I have to look into that). So I create a second virtual defined as 33001:1:2. Now I can send commands from master 2 to that, and receive them on master 1, then pass them along to 33001:1:1.
  • Reese JacobsReese Jacobs Posts: 347
    Multiple System Communication (AS16 Problem)

    Dave,

    Today is your lucky day for an answer to your question.

    We too had a multi-room setup using 2 local room Masters and a central Master with an AS16 connected to the central Master. We defined the virtual device for the central Master AS16 on the 2 local Masters and discovered, as you have, that it did not work as expected for SEND_COMMANDs to control the switcher. We ended up doing exactly as you did - implementing a virtual device for the passing of commands back and forth to the central Master which in turn sends the actual device commands to the switcher. I am not sure where we ended up on the issue of levels and channels in terms of their ability to work correctly so I can't offer any conclusions with respect to those.

    When we discovered the problem, we scratched our heads since this was an ideal use of Master to Master. We experimented with numerous workarounds and finally spoke with a Landmark guru at AMX Tech Support. He confirmed that this is a known problem and in fact attributed the problem to a firmware issue in the AS16. It was not clear to me how the AS16 firmware could be the issue but he was very aware of the problem, knew it would not work, and told us the workaround was precisely what we both implemented. The moral of the story is that not all virtual devices and physical devices are created equal with respect to Master to Master.

    I ran into similar issues (although not Master to Master related) trying to do things on the virtual device associated with DMS keypads. I had some code that was triggered under a BUTTON_EVENT for a touchpanel that in turn I wanted to trigger a channel event for a DMS. I tried to DO_PUSH on the DMS virtual device only to find that DO_PUSH can't be used on DMS virtual devices whether they be local or remote to the Master.

    Reese
  • DHawthorneDHawthorne Posts: 4,584
    Hm, so this is particular to the AS8/16, and not a general virtual device limitation. I would love to know what the internal mechanics are that make it behave this way.
  • DHawthorneDHawthorne Posts: 4,584
    Anyhoo, back to the original post, I would synchronize simple variables with a virtual device and levels. Define the virtual in each master identically, and use CREATE_LEVEL on each master to bind the local copy of the variable to the same level number on the virtual. If the local master updates the variable, it needs to do a SEND_LEVEL to the virtual, which will automatically then update the variables on all the other masters.

    This works for simple variables, but obviously won't do for something very complex, like a large array. For that, you would probably be best served by passing messages for the individual fields that need to be updated as needed. I prefer using levels and channels when I can with inter-master communications because they are handled on a much lower level and therefor eat up far less processing resources, but it isn't always practical.
  • Reese JacobsReese Jacobs Posts: 347
    Multiple System Communication (AS16)

    Dave,

    The problem with the AS8/AS16 is not an inherent limitation of virtual devices as you stated. Although I am speculating, I suspect the limitation extends to other Landmark devices like the AMP8. The DMS, MSP (PHASTlink version), and RF/IRI devices are also handled very similarly since they are essentially Landmark devices with firmware and Netlinx module support for controlling them using a Netlinx system. I suspect all of the devices in this category have unique limitations including but not limited to interacting with them through virtual devices in Master to Master configurations.

    Reese
  • maxifoxmaxifox Posts: 209
    DHawthorne,

    Virtual device must carry system number of 0. I think, since you defined them with different system number this created those odd problems...
  • Reese JacobsReese Jacobs Posts: 347
    Multiple System Communication

    I am not aware of any restriction which requires a virtual device to carry a system number of 0. In Dave's case of the AS8/AS16, trying to send a command to a remote AS8/AS16 device using the virtual device defined on the remote system for the module interaface does not work but this is due to AS8/AS16 limitations and not limitations per se on the use of virtual devices between systems.

    I have developed numerous systems which rely on remote system definitions for virtual devices and these all work as expected. I have a hotel application where a main Lutron module receives channel events from 35 remote Masters using virtual devices for the purpose of generating lighting actions on phantoms keypads. The main Lutron module defines the virtual devices for all 35 of the remote systems and does so using their system numbers. This system has worked flawlessly for over a year.

    I think in concept and in practical use, remote system references in virtual devices are fine. The AS8/AS16 case turned out to be a unique situation where it would not work and I suspect similar problems would exist with DMS, RF/IRI, and MSP Landmark devices and their modules under Netlinx.

    Reese
  • wcravenelwcravenel Posts: 114
    While not as large as Reese's project, I too have coded to one master and had other master's devices simply be part of that code. Ie. all Lutron code or audio switch code resides on the master (say, #1) to which Lutron/switch is connected; TPs on systems #2 - #n simply have the appropriate port defined on master #1. Arrays, virtuals, combines have all worked fine (so far). Can't act on that code/variables/etc with another master, though.
  • maxifoxmaxifox Posts: 209
    Reese, I was wrong about zero for virtual, that's not a requirement.

    By the way, it is always a challenge to decide what code goes where in a system with multiple masters... Any rules of thumb?
  • DHawthorneDHawthorne Posts: 4,584
    maxifox wrote:
    Reese, I was wrong about zero for virtual, that's not a requirement.

    By the way, it is always a challenge to decide what code goes where in a system with multiple masters... Any rules of thumb?
    As a rule of thumb, I put the code on the master that will be physically connected to the controlled device. There are times, however, when that is just not feasible (for example, if the code on one master needs to see values changed by such a device on another). However, there is absolutely nothing stopping you from putting all your code on a single master and just using the others to drive the devices. My usual topology, though, is a central master that handles all common functions, then local masters that control subsystems, and each carries the code to handle the functions they are responsible for. That way, if there is a communications glitch, the local systems still work locally.
  • Reese JacobsReese Jacobs Posts: 347
    Multiple System Communication
    By the way, it is always a challenge to decide what code goes where in a system with multiple masters... Any rules of thumb?
    Excellent question!

    I follow many of the same guidelines that Dave described. In general, I try to place module/driver code for devices on the Master to which the devices are connected. For example, I would never define a serial device as 5001:1:100 and try to control it Master to Master. It is not that it should (or would) not work, I just don't think it is prudent. I have no problem defining remote touchpanels or remote virtual devices (for interfacing) and I do this frequently. I have had very reliable and efficient results with channel, button, and level events in Master to Master configurations and I do not hesitate to use these as needed. DATA_EVENTs are of course highly effective for handling online and offline events for remote devices as well as exchanging interface data using STRINGs or COMMANDs. When I first started using Master to Master, I was worried about latency and dropped packet potential but these worries proved unfounded provided of course the network is rock solid and performs well.

    That is perhaps the only other guideline I would provide on Master to Master. The network is critical for Master to Master to operate effectively and efficiently. Over a carefully implemented high performance LAN, Master to Master will work great. However, like any node, if the LAN has problems, then you will likely see problems in Netlinx. I think you also need to be very careful about Master to Master in a WAN configuration. I have done Master to Master over a WAN using a VPN connection and high speed DSL on boths ends but you can't really control the intermediate network hops.

    In summary, I tend to organize my Masters around subsystems and I use Masters to control the devices that are attached to them whether it is serial, IR, I/O, or Relay. I use channel, button, or level events to communicate between Masters as well as STRINGs and COMMANDs. In rare instances, I will use IP_CLIENT_OPEN on one Master and IP_SERVER_OPEN on another to implement a specific (and reliable) protocol for Master to Master. In general though, I let Netlinx do the heavy lifting for Master to Master through the URL list and this has proven reliable and effective.

    Reese
  • Master to master comms

    I once programmed a system with four different NXI's in four different cities, connected over a private IP network by the local telco. I used UDP.
    Each master used Port 2 for UDP receive and higher ports to talk to the others. Each master stores the outgoing messages in a queue, and resends them every second until the destination acknowledged them, or after 30 attempts. This is rock solid, overcomes network delays and intermittent connection errors, and has been working for a couple of years now with no problems. Where to put the code? Nearest master to where it's used. The ideal is that the system should continue to work locally if the comms fails.
  • maxifoxmaxifox Posts: 209
    JohnCharlton, your design looks unusual for me and I have a few questions... Could you please tell why did you use UDP and then acknowledgement instead TCP? What about standard URL list?
  • Advantages of UDP
    maxifox wrote:
    JohnCharlton, your design looks unusual for me and I have a few questions... Could you please tell why did you use UDP and then acknowledgement instead TCP? What about standard URL list?

    As you probably know, UDP is fire and forget, there are no smarts involved.
    This allows the programmer to "re-invent the wheel" (as we do) so as to get something that works reliably in the particular circumstances. The network this system was using had some long and unpredictable latencies (i.e. delays) which the standard TCP timings didn't cope with, things would go off-line and on-line unpredictably. The UDP method allowed me to fire numbered messages at the other systems and repeat sending them at one second intervals until they were acknowledged. Each message had a header that included the sending system ID and the unique reference number. When things were quiet the systems would send watchdog messages to each other every 10 seconds to monitor the links - I implemented this sending the string 'DOG' and the reply was 'ACK' followed by the reference number.

    Ihave also used TCP, which works fine for networks that don't have long, unpredictable delays.

    Hope this helps.
  • maxifoxmaxifox Posts: 209
    Quite interesting solution. Since they introduced IP functionality I was wondering where UDP might be really useful. Thanks for pointing out.
Sign In or Register to comment.