Menu

Support

Roboteq supports Ethernet TCP/IP connection on the FBL2 and GBL2 series of controllers. Connecting these controllers to a WiFi network can be done using a simple and inexpensive WiFi to Ethernet Access point.

 fbl2360e with wifi ap

For this demonstration we selected WiFi Access Point made by VONETS, model VAP11G-300. An RJ45 cable plugs into the Ethernet sockets found on the FBL2360E and the Access Point. The Access Point's power supply cable is connected to the controller's 5V output. 

The first thing to do is to connect the Access Point to the WiFi network. Different Access Points use different methods but typically require that they be first connected to a PC via Ethernet, or by WiFi (the Access Point initially acts as a WiFi server). With the Browser pointing to the Access Point IP address, we can configure the Access Point to connect into our WiFi network. 

Once this is done, the motor controller is connected to the WiFi network via its RJ45 port. To enable RoboteQ’s motor controller access on the ethernet port, open Roborun+ and at the configuration tab, we should be able to configure the TCP Mode as Enabled, as shown in the image below.

tcpimemenu

Note that the products supporting Ethernet communication are marked with the letter “E” after the Controller model number.

Connect the access point on the motor controller using an Ethernet cable. Since the pc in connected via WiFi on the access point’s local network and the controller is connected via an ethernet cable on the access point, using the motor controller utility select TCP as the COM Port.

tcpipselect

At the pop-up window, which will appear after setting the COM Port to TCP, fill in the IP and Port fields and press ok.

ipaddress

After pressing ok, the virtual com port connection will be lost with the controller and the controller will be found via TCP.

Controlling, monitoring and configuring RoboteQ’s motor controller are now available via a WiFi connection.

RFID tags and antenas are a cost effective and efficient method for determining the location of a robot along its track. CANOpen RFID reader/writers are a challenge to interface directly to a motor controller. This is because CANOpen is a master/slave architecture and both the RFID antena and the motor controller are slave devices. In a typical system, a CANOpen master (a PLC for example) must fetch data from the antena and send it to the controller.

Thanks to scripting and the RawCAN protocol, a Roboteq motor controller can be made to operate as simple CANOpen master, enable the RFID antena, and then capture and parse the data sent. RawCAN is a very low-level implementation for manipulating CAN data using scripting commands.

This example shows how to interface a DTC510 RF ID sensor from IFM Electronics work and communicate with our motor controller. It is a CANOpen slave device. So in order to communicate with it we configured the motor controller as RawCAN with listen Node ID as 0. Listening to node ID 0 disables the node address filter so that the controller can see all frames on the CAN bus (the controller acts like a CAN sniffer)

riid antenatag

By default the Node id of the RFID sensor is 32 and the bit rate is 125kb/sec. These can be changed using SDOs.

The script in the controller first constructs and send the CANOpen NMT message in order to set the DTC510 state to operational. Then at each status change the sensor sends TPDO1 which holds the device status (VAR 2), including the info whether there is tag detected or not (VAR 2).

When a tag is detected the sensor sends TPDOs 2, 3, 4 with the 40 first bytes of the tag's tag id.

We can also write data to each tag. We implemented in the script the write and erase (set 0) the tag id. For more details check the script's Header comments.

 

'DTC510 Reader
'Created by Roboteq Inc.

'The script can:
' * Read the 40 first bytes of the tag ID
' * Write the first 8 bytes of the tag ID and
' * Erase the first 8 bytes of the tag ID.

'VAR 1: 0 Reads the tags
' 1 Writes to the 0 - 8 bytes of the tags specific tag id, only if the tag id is 0.
' 2 Erases the tag id
'VAR 2: Displays the Device Status of DTC510
'VAR 3: Displays 1 if a tag is detected, 0 if not.
'VAR 4: Displays the 0 - 4 bytes of the tag id.
'VAR 5: Displays the 4 - 8 bytes of the tag id.
'VAR 6: Displays the 8 - 16 bytes of the tag id.
'VAR 7: Displays the 16 - 24 bytes of the tag id.
'VAR 8: Displays the 24 - 32 bytes of the tag id.
'VAR 9: Displays the 32 - 40 bytes of the tag id.

Option Explicit

#define DTC510_NODEID 32 'default to be changed with SDO indexes 0x20F0, 0x20F1
#define DTC510_BITRATE 4 'default 125kbits/s to be changed with SDO indexes 0x20F2, 0x20F3

'define TAGID_BYTE1 WriteCounter
#define TAGID_BYTE2 0x00
#define TAGID_BYTE3 0x00
#define TAGID_BYTE4 0x00
#define TAGID_BYTE5 0x00
#define TAGID_BYTE6 0x00
#define TAGID_BYTE7 0x00
#define TAGID_BYTE8 0x00

#define READ_DATA 0
#define WRITE_DATA 1
#define ERASE_DATA 2

Dim WriteCounter As Integer
Dim TriggerCounter As Integer
Dim Action As Integer
Dim Header As Integer
Dim DeviceStatus As Integer
Dim Present As Integer
Dim PrevPresent As Integer
Dim OkToWrite As Integer
Dim NewTagState As Integer
Dim tag[5] As Integer

WriteCounter = 0
TriggerCounter = 0

'Set Node to Operational Node
setcommand(_CS, 1, 0) 'Header of NMT messages is 0
setcommand(_CS, 3, 1) 'Go to operational
setcommand(_CS, 4, DTC510_NODEID)
setcommand(_CS, 2, 2)
top:
'print(Action,"\t",WriteCounter,"\t",TriggerCounter,"\t",Present,"\t",tag[0],"\t",tag[1],"\r")
wait(100)
Action = getvalue(_VAR,1)
while(getvalue(_CF) <> 0)
Header = getvalue(_CAN,1)
if(Header = 0x180 + DTC510_NODEID)
DeviceStatus = getvalue(_CAN,3) + (getvalue(_CAN,4) << 8) + (getvalue(_CAN,5) << 16) + (getvalue(_CAN,6) << 24)
if(DeviceStatus and 0x0004)
Present = 1
else
if(Present = 1)
NewTagState = 1
end if
Present = 0
end if
setcommand(_VAR, 2, DeviceStatus)
setcommand(_VAR, 3, Present)
elseif(Header = 0x280 + DTC510_NODEID)
tag[0] = getvalue(_CAN,3) + (getvalue(_CAN,4) << 8) + (getvalue(_CAN,5) << 16) + (getvalue(_CAN, 6) << 24)
tag[1] = getvalue(_CAN,7) + (getvalue(_CAN,8) << 8) + (getvalue(_CAN,9) << 16) + (getvalue(_CAN,10) << 24)
setcommand(_VAR, 4, tag[0])
setcommand(_VAR, 5, tag[1])
if(Present <> PrevPresent)
NewTagState = 1
end if
elseif(Header = 0x380 + DTC510_NODEID)
tag[2] = getvalue(_CAN,3) + (getvalue(_CAN,4) << 8) + (getvalue(_CAN,5) << 16) + (getvalue(_CAN, 6) << 24)
tag[3] = getvalue(_CAN,7) + (getvalue(_CAN,8) << 8) + (getvalue(_CAN,9) << 16) + (getvalue(_CAN,10) << 24)
setcommand(_VAR, 6, tag[2])
setcommand(_VAR, 7, tag[3])
elseif(Header = 0x480 + DTC510_NODEID)
tag[4] = getvalue(_CAN,3) + (getvalue(_CAN,4) << 8) + (getvalue(_CAN,5) << 16) + (getvalue(_CAN, 6) << 24)
tag[5] = getvalue(_CAN,7) + (getvalue(_CAN,8) << 8) + (getvalue(_CAN,9) << 16) + (getvalue(_CAN,10) << 24)
setcommand(_VAR, 8, tag[4])
setcommand(_VAR, 9, tag[5])
end if
'print(Header,"\t",Present,"\t",PrevPresent,"\t",DeviceStatus,"\r")
end while
if(NewTagState = 1)
if(Present = 1)
print("Tag Found With Tag Id = ", tag[0],"\r")
else
print("Tag Not Detected\r")
end if
NewTagState = 0
OkToWrite = 1
PrevPresent = Present
else
OkToWrite = 0
end if
if(Action <> 0 and Present = 1 and OkToWrite)
'Write Data
setcommand(_CS, 1, 0x300 + DTC510_NODEID) 'Header of RPDO 2
if(Action = WRITE_DATA and tag[0] = 0)
WriteCounter = getvalue(_VAR,10)
'Here you can play with the tag ids you want to use
setcommand(_CS, 4, TAGID_BYTE2) 'SetData
setcommand(_CS, 5, TAGID_BYTE3) 'SetData
setcommand(_CS, 6, TAGID_BYTE4) 'SetData
setcommand(_CS, 7, TAGID_BYTE5) 'SetData
setcommand(_CS, 8, TAGID_BYTE6) 'SetData
setcommand(_CS, 9, TAGID_BYTE7) 'SetData
setcommand(_CS, 10,TAGID_BYTE8) 'SetData
print("Tag written\r")
elseif(Action = ERASE_DATA)
WriteCounter = 0
setcommand(_CS, 4, 0) 'SetData
setcommand(_CS, 5, 0) 'SetData
setcommand(_CS, 6, 0) 'SetData
setcommand(_CS, 7, 0) 'SetData
setcommand(_CS, 8, 0) 'SetData
setcommand(_CS, 9, 0) 'SetData
setcommand(_CS, 10,0) 'SetData
print("Tag erased\r")
else
goto top
end if
setcommand(_CS, 3, WriteCounter) 'SetData
setcommand(_CS, 2, 8)
if(TriggerCounter = 1)
TriggerCounter = 0
else
TriggerCounter = 1
end if
setcommand(_CS, 1, 0x200 + DTC510_NODEID) 'Header of RPDO 1
setcommand(_CS, 3, TriggerCounter) 'SetData
setcommand(_CS, 4, 0) 'SetData
setcommand(_CS, 5, 0) 'SetData
setcommand(_CS, 6, 0) 'SetData
setcommand(_CS, 7, 0) 'SetData
setcommand(_CS, 8, 0) 'SetData
setcommand(_CS, 9, 0) 'SetData
setcommand(_CS, 10,0) 'SetData
setcommand(_CS, 2, 8)
end if
goto top

 

 

 

Advanced Topics in Data Logging and Time Series Analysis

Monitoring the performance of a RoboteQ motor controller is essential to mastering the usage of our motor controllers. In this article, we will be demonstrating the advanced techniques that RoboteQ engineers use when setting up a motor controller, deploying a controller in a field application, or troubleshooting the performance of a motor control setup by datalogging and analyzing values.

Prerequisites

This article also assumes that you are familiar with general RoboteQ terminology, including our operating modes (Open Loop, Closed Loop, etc.) and some of the internal interfaces for commanding values from our motor controller (Motor Commands, Feedback Signal, etc.). If you are not familiar with any of these terms in the context of RoboteQ products, please consult our User Manual.

Open Loop Motors - a Quick Rundown

One of the first tasks that occur when connecting a controller to a motor is to ensure that the controller configuration is correct, and that all hardware connections to the motor are working. The first step is always to run the motor in Open Loop mode. From Page 86 our User Manual:

In [Open Loop] mode, the controller delivers an amount of power proportional to the command information. The actual motor speed is not measured.

The best way to think of Open Loop control is as a direct voltage control. The Motor Command issued to an Open Loop Motor channel, the supply voltage is proportionally applied to the motor output. The formula for this application is given as:


DPWM = .1% * Mc

Where DPWM is the output PWM signal duty cycle, or the Motor Power, and MC is the Motor Command. For practical purposes, you can think of the output duty cycle as the voltage output of the controller.

Note: Keep in mind that for Brushless and AC induction controllers, the output voltage is not a DC current. For Brushless controllers, it is commuted based on the controller’s Switching Mode. In an AC Induction controller, it is output as a 3 phase AC signal. However, in both of these controllers, the output is still in the form of a PWM signal, so the analogy still holds.

Therefore, when we drive a motor in Open Loop mode we want to make sure the following occurs:

  • When we send the channel a Motor Command, the motor power quickly responds.
  • That the Motor Power of the controller changes at a fixed ramping speed until it reaches the Motor Command value, and then it stays there.
  • That, as the rotor of the motor applies torque, we see current drawn, or Motor Amps

Creating a Log

Using the Run Tab in Roborun+ we can log data values from the controller to ensure that the previous three conditions are occurring. This is the output of a Brushed Motor running in Open Loop Mode on an SDC2160:

markdown img paste 20181121152240183

Running this MicroBasic Snippet:

top:
    setcommand(_G, 1, 1000)
    wait(3000)
    setcommand(_G, 1, 0)
    wait(3000)
    setcommand(_G, 1, -1000)
    wait(3000)
    setcommand(_G, 1, 0)
    wait(3000)
goto top

Here it looks like our controller is achieving the first two parameters that we are looking for: it is accepting new Motor Commands and it is adjusting Motor Power correctly in Open Loop mode. However, by looking at the Run Tab graph, it would appear that the motor isn’t drawing current. Perhaps we should take a closer look at the Data…

Saving and Examining a Log

By hitting the save button (markdown img paste 20181121154948678) we can save a log of the actual samples that the run tab is using as a Tab column delimited, newline row delimited text file. For instance, here is an excerpt of a log saved of the above Dataset:

Time Stamp            Motor Power 1 Motor Command 1 Battery Amps 1
11/21/2018 3:21:28 PM   0   0   0
11/21/2018 3:21:28 PM   0   0   0
[...]
[...]
11/21/2018 3:21:29 PM   0   0   0
11/21/2018 3:21:29 PM   0   0   0
11/21/2018 3:21:29 PM   0   0   0
11/21/2018 3:21:30 PM   176 1000    0
11/21/2018 3:21:30 PM   376 1000    0.1
11/21/2018 3:21:30 PM   576 1000    0.2
11/21/2018 3:21:30 PM   776 1000    0.2
11/21/2018 3:21:30 PM   976 1000    0.2
11/21/2018 3:21:30 PM   1000    1000    0.1
11/21/2018 3:21:30 PM   1000    1000    0.1
11/21/2018 3:21:30 PM   1000    1000    0.1
11/21/2018 3:21:30 PM   1000    1000    0.1
11/21/2018 3:21:30 PM   1000    1000    0.1
11/21/2018 3:21:31 PM   1000    1000    0.1
11/21/2018 3:21:31 PM   1000    1000    0.1
11/21/2018 3:21:31 PM   1000    1000    0.1
11/21/2018 3:21:31 PM   1000    1000    0.1
11/21/2018 3:21:31 PM   1000    1000    0.1
11/21/2018 3:21:31 PM   1000    1000    0.1
11/21/2018 3:21:31 PM   1000    1000    0.1
11/21/2018 3:21:31 PM   1000    1000    0.1
11/21/2018 3:21:31 PM   1000    1000    0.1
11/21/2018 3:21:31 PM   1000    1000    0.1

Here we can see the raw values that the run tab has logged from the controller. Now it is clear - the motor was drawing current! Just not very much, since it was an unloaded motor.

When you save a log of the controller values, each sample is given it’s own time stamp, in the format of MM/DD/YYYY (H)H:MM:SS. Notice how their are currently 10 samples per second in the log. What if we want a higher resolution sample? What is preventing this? If we look at the Controller Log form the console tab, we get our answer:

markdown img paste 2018112116011573

The controller isn’t just debugging the values we want to log, it is also sending tons of other values, such as Analog Input values (AI) or the Pulse Input values (PI). These values debugs are actually what is going on under the hood to power the rest of the run tab status lights. We can disable it Using the checkmark boxes in each section:

markdown img paste 20181121160838664

And when we check the log generated with the sections disabled:

Time Stamp  Motor Power 1   Motor Command 1 Battery Amps 1
11/21/2018 4:03:51 PM   0   0   0
11/21/2018 4:03:51 PM   0   0   0
11/21/2018 4:03:51 PM   0   0   0
11/21/2018 4:03:51 PM   0   0   0
11/21/2018 4:03:51 PM   0   0   0
11/21/2018 4:03:51 PM   0   0   0
11/21/2018 4:03:51 PM   0   0   0
11/21/2018 4:03:51 PM   0   0   0
11/21/2018 4:03:51 PM   0   0   0
11/21/2018 4:03:51 PM   0   0   0
11/21/2018 4:03:51 PM   0   0   0
11/21/2018 4:03:51 PM   0   0   0
11/21/2018 4:03:51 PM   0   0   0
11/21/2018 4:03:51 PM   0   0   0
11/21/2018 4:03:51 PM   0   0   0
11/21/2018 4:03:51 PM   0   0   0
11/21/2018 4:03:51 PM   0   0   0
11/21/2018 4:03:51 PM   0   0   0
11/21/2018 4:03:51 PM   0   0   0
11/21/2018 4:03:51 PM   0   0   0
11/21/2018 4:03:51 PM   0   0   0
11/21/2018 4:03:51 PM   0   0   0
11/21/2018 4:03:51 PM   0   0   0
11/21/2018 4:03:51 PM   0   0   0
11/21/2018 4:03:51 PM   0   0   0
11/21/2018 4:03:51 PM   0   0   0
11/21/2018 4:03:51 PM   0   0   0
11/21/2018 4:03:51 PM   0   0   0

We get almost 30 samples per second. We can get even more if we increase the Baud settings of the controller, however the minimum time between samples will be 10ms (100Hz sample rate).

Graphing a Log Using Excel

We have designed our data logs to be very accessible to tabular data programs. Using an external program it becomes very easy to exam our data using a program like Excel. For instance, let’s paste the contents of the first Open Loop log we generated into Excel:

  1. First copy the contents of your motor log.
  2. Then Highlight cell A1 in a blank Excel table:
  3. markdown img paste 20181121162234359
  4. And finally, paste your log (Ctrl+V)

markdown img paste 20181121161913240

Excel is automatically able to parse the delimited data and separate each column into rows and columns. Make sure you have A1 highlighted when you paste, or it may not automatically parse the data correctly.

Once the data is in excel, we can take advantage of Excels rich graphing features, wich are far beyond the capabilities of the graph previewer that is included in the run tab of Roborun+. All we have to do is insert an XY scatter plot with our data selected:

markdown img paste 20181121163527606

And Voila!

markdown img paste 20181121163722736

… Or not. Excel had a little bit of trouble with the data selection. We have to help it out by deleting the range for our Horizontal Axis Labels. Just right click and choose “Select Data”:

markdown img paste 20181121163934942

Click the Edit Button for the Horizontal Axis Labels:

markdown img paste 20181121164059760

And delete eveything in the Axis label range before clicking okay:

markdown img paste 20181121164217131

And we are left with a beautiful excel scatter plot:

markdown img paste 20181121164428205

Ah, that’s much better.

Analyzing our Data with Python and NumPy

We can use other tools than Excel to manipulate our data. If we want to perform advanced analysis, importing the data to Python is not a bad idea. In Python we can use a variety of tools to manipulate and perform analysis on our motor logs.

Let’s import our motor logs into a NumPy array in Python. Here is a snippet that does that

import numpy
 
MotorData = np.genfromtxt('Brushed_OpenLoop.txt', skip_header = 1) #Skip data label headers
MotorData = MotorData[:, 3:] #skip time frame columns

Like Excel, NumPy will also automatically parse our data. In the above example, I also took the liberty of skipping the series label header (skip_header = 1) as well as stripping away the timestamps (MotorData[:, 3:]).

Once we have the data as a NumPy array, analysis becomes a breeze. For instance, sticking on the topic of plotting the data, we can use plot.ly to generate an interactive graph:

 py

The sky is the limit when it comes to manipulating the data behind our motor logs and gaining insight about the performance of the RoboteQ motor controller. If you can’t perform some cool motor analysis using our data logging, drop This email address is being protected from spambots. You need JavaScript enabled to view it. an email and let us know.

Safety is a critical concern in Mobile Robots. Serious injury to person and/or expensive material damage can occur if the robot and its load run out of control. Laser range finders, remote controls and other systems can be used to tell the robot to stop. The challenge is to make the robot always respond to the stop command. This is where Safe Torque Off – or STO – comes in.

STO is a safety mechanism for motor drives that reliably brings the motor to a no-torque state. STO is typically used for the prevention of an unexpected startup (EN 1037) of machinery or for an emergency stop, fulfilling stop category 0 (EN 60204-1).

 

sto

 

STO has the immediate effect that the drive cannot supply any torque-generating energy. STO can be used wherever the drive will be brought to a standstill in a sufficiently short time by the load torque or friction or where coasting down of the drive is not relevant to safety. In a Mobile Robot application, STO will stop motion in case of emergency, and prevent restart until it is safe to do so.

From this simple description, one can assume that STO is as simple as disconnecting power to the drive and motors. And indeed, STO can be achieved using a contactor that will cut the power to the motor controller, for example. However, using a contactor adds cost and components that can eventually go wrong.

STO must operate according to Safety Category 3 Performance Definition. To achieve Safety Category 3, according to EN ISO 13849-1, the controller must meet a list of several requirements. Of this list, the most challenging is that the STO must function even in the case of a single fault in any part of the system.

So, in the case of our earlier example, a single contactor cannot be use. At a minimum, two contactors are needed in series, so that energy can be cut from the motor in case one of the two contactors gets stuck.

 

Embedding STO in a Controller

All drive manufacturers are free to invent any method they wish if it meets the safety requirements. The most common implementation – and the one used by Roboteq, is to add a circuit that will cut off the power to MOSFET drivers. Without power, the drivers are not able to turn on any of the MOSFET’g gate.

Two switches in series are necessary to ensure that the power does get cut even if one of the switches is permanently ON because of failure.
Each of the switches is driven by a separate input, commonly labeled STO1 and STO2. In this manner, too, if one external or internal circuit is damaged and the respective STO command is stuck at the “ON” level, the other can still safely disconnect the power to the drivers.

 

Asset 1

 

The MCU monitors the STO input lines and the voltage to the MOSFET drivers. It is important to notice, however, that the STO circuit works independently of the controller’s MCU. It is therefore totally immune to any hardware malfunction.

The Safety Standard also requires that the drive be able to detect a failure in the STO circuit, and this can be quite challenging. Consider the example below.

STO1 and STO2 are active and both switches are On. But switch 1 is damaged and will remain ON even if the STO1 command is off. The drive appears to be operating normally. However, it is no longer as safe because it would not turn off if STO1 only is deactivated. It will still stop because STO1 and STO2 will be off. But if there is another fault in the system and should the STO2 command wire be stuck to a high voltage, the controller will not stop.

To alleviate these sort of problems, the controller incorporates additional circuitry for detecting and reporting that the STO circuit is fully functional.

The controller design is such that MCU can force either of both STO inputs to the OFF state. The MCU will use this capability to briefly turn off the MOSFET driver supply and verify that the driver supply voltage does in fact drops. This check is performed every time the controller is powered ON, as well as at periodic intervals.

Note that the MCU is not physically capable to force the STO inputs to the ON state. If it was, this could cause the STO circuit to cease protecting, in case the MCU is accidentally setting the outputs to 1 due to software of hardware malfunction.

Being a safety critical function that absolutely has to work in all situations, STO must be certified by a regulatory organization such as TUV. There, the examiner simulates the failure of all critical components to verify that the drive can still safely be stopped.

STO is available now on Roboteq's FBL2360T controllers. STO will be progressively introduced to all our motor controller products.

 

Subcategories

Tips and Techniques to Common Problems

Go to top