FlexSEA Wiki

A WEARABLE ROBOTICS TOOLKIT

User Tools

Site Tools


i2t

I²t current limit: Programmable Fuse

FlexSEA-Execute (Ex) and FlexSEA-Regulate (Re) have a software I²t protection. This algorithm allows the user to select limits for average and peak currents (of a certain duration). It is essentially a programmable fuse that can be used to protect the circuits, but also systems built with FlexSEA and users testing them.

Theory of operation

Fundamentals

Based on the application we calculate a current-time curve. Similar to the curves found in fuse datasheets, it indicates how long a given current will be allowed to flow before the fuse interrupts the flow (blows). The three most important parameters are:

  • Maximum average current: if the current stays below this value the protection will never engage
  • Current limit: combined with the time, this determines the maximum pulse supported
  • Time at current limit: combined with the current limit, this determines the maximum pulse supported

For example, if we program a maximum average current of 5A and a current limit of 30A for 2.5s we obtain the following curve:

  • 5A is on an asymptote: infinite time
  • If 30A flows for more than 2.5s the protection will engage
  • If the pulse is 10A the trip time will be around 30s

Non-linearity

The whole point of the I²t algorithm is to model thermal dissipation and prevent dangerous conditions. Because of the power of two, peaks can lead to significant heating. The current sensors used by FlexSEA have limits ranging from 5A to 30A depending on the hardware version. While they will tolerate peaks above their maximum, they will only report up to their max. Using a 30A sensor as an example, if our current is 42A the energy is doubled versus 30A yet the sensor will report 30A. An optional non-linearity was added to deal with those conditions. Simply, if you get close to the sensor's maximum range you can artificially increase its sensitivity to protect your hardware.

Without the non-linearity:

CURR = maxAvgCurrent:1000:30000;
tmp = (CURR./SCALE).^2;
time = (I2T_LIMIT * dt) ./ ( tmp - I2T_LEAK );

With the non-linearity:

CURR = maxAvgCurrent:100:1.5*currentLimit;
CURR2 = (max(0,(CURR-NON_LIN_TRESH)));
tmp = ((CURR+10*CURR2)./SCALE).^2;
time = (I2T_LIMIT * dt) ./ ( tmp - I2T_LEAK );

As can be seen on the plot below, below the threshold the algorithm behaves the same. Above the threshold (set at 16A in this example) we can see that the protection trips faster with the non-linearity.

Calculating and Programming

To minimize the processor load we convert the user parameters to constants on a PC. The embedded firmware uses the pre-calculated constants.

The constants can be obtained from the Plan GUI or from a Matlab/Octave script. The GUI is simpler, but Octave outputs a plot that can help you select the optimal parameters.

The user parameters are:

  • Maximum average current (mA): if the current stays below this value the protection will never engage
  • Current limit (mA): combined with the time, this determines the maximum pulse supported
  • Time at current limit (s): combined with the current limit, this determines the maximum pulse supported
  • Non-linear threshold (mA): inflection point for the non-linearity. Must be between the maximum average current and the current limit.
  • Shift: conversion from mA to 'ticks'. More info below.
  • Enable non-linearity: check (set to 1) if you want that feature, uncheck (set to 0) if not.

Shift: The algorithm uses 8-bit values (0-255) while the current sensor is rated with real current in mA (ex.: 30000mA). We need to scale down the maximum current accordingly. If your hardware is equipped with a ±30A sensor (±30000mA) the ratio between 30000 and 256 is 117. For maximum efficiency we use a bit shift instead of a division. The closest (and higher) shift is 7, equivalent to a division by 128. For ActPack users this value will not need to be changed: use the default 7.

Plan GUI

  1. Open Plan
  2. Tools > “Calibration & System”
  3. Safety tab

The built-in calculator will compute the required constants from the user parameters. The tool can write the values directly to Re. Please note that the Ex I²t is not currently user programmable - contact Dephy if you need different values than the default.

The settings will be saved in non-volatile memory and will take effect at the next power cycle.

Matlab/Octave

The Matlab/Octave script below allows users to generate the proper constants for the C code. The example uses 10A average, a peak of 15A for no longer than 1s, and a non-linearity at 17.5A.

% I2t current limit: user
% JFDuval, Dephy, Inc. 06/14/2017
% Update August 2018: Added non-linearity
% Update December 2018: Cleaner code and output
 
% Note: use this file to get your #define values. i2t_1.m can be used to test
% your values with different profiles.
 
clc;
close all;
clear all;
format short eng
 
% Period, i2t_compute() call:
dt = 100e-3;      %Every 100ms
Y_TIME_MAX = 20;  %Max time plotted, in seconds
 
disp('Program these values in i2t-current-limit.h:')
disp('============================================')
 
% The algorithm uses 8-bit values: we need to scale down the maximum current
% accordingly. It uses real units (mA). Ex.: ±30000mA sensor
% 30000/256 = 117 => shift 7 (div by 128). 30A will give us 234
 
% Pocket has a ±5A sensor. 5000/256 = 19.53 => shift by 5 (32)
 
I2T_SHIFT = 7             % Closest bitshift available
SCALE = 128;              % (Octave only, avoids bitwise operations)
NON_LIN_TRESH = 17500;    % mA
 
% Maximum average current you want to support:
maxAvgCurrent = 10000;     %mA
I2T_LEAK = (maxAvgCurrent / SCALE)^2
 
% Maximum peak current you want to support, and duration:
currentLimit = 15000;       %mA
currentLimitTime = 1;     %s
I2T_LIMIT = (currentLimitTime / dt) * ((currentLimit/SCALE)^2 - I2T_LEAK)
 
%At what fraction of the max to you want a warning? (0-1)
warn = 0.8;
I2T_WARNING = warn * I2T_LIMIT;
 
%8-bit non-lin:
I2T_NON_LINEAR_THRESHOLD = NON_LIN_TRESH / SCALE
 
% Plotting:
CURR = maxAvgCurrent:100:2.5*currentLimit;
CURR2 = (max(0,(CURR-NON_LIN_TRESH)));
tmp = (CURR./SCALE).^2;
tmpNL = ((CURR+10*CURR2)./SCALE).^2;
time = (I2T_LIMIT * dt) ./ ( tmp - I2T_LEAK );
timeNL = (I2T_LIMIT * dt) ./ ( tmpNL - I2T_LEAK );
figure()
plot(CURR, time)
title('Time before reaching the I2t limit')
xlabel('Current (mA)')
ylabel('Time (s)')
ylim([0,Y_TIME_MAX])
xlim([0.9*maxAvgCurrent,1.25*max(currentLimit,NON_LIN_TRESH)])
hold on
plot(CURR, timeNL, 'r')
legend('Original', 'Non-linear')
 
disp('')
disp('Time at given current (mA):')
CURR = 25000
CURR2 = (max(0,(CURR-NON_LIN_TRESH)));
tmp = (CURR./SCALE).^2;
tmpNL = ((CURR+10*CURR2)./SCALE).^2;
time = (I2T_LIMIT * dt) ./ ( tmp - I2T_LEAK )
timeNL = (I2T_LIMIT * dt) ./ ( tmpNL - I2T_LEAK )

The script will output constants, and a plot:

Program these values in i2t-current-limit.h:
============================================
I2T_SHIFT = 7.0000e+000
I2T_LEAK = 6.1035e+003
I2T_LIMIT = 76.2939e+003
I2T_NON_LINEAR_THRESHOLD = 136.7188e+000

Time at given current (mA):
CURR = 25.0000e+003
time = 238.0952e-003
timeNL = 12.6263e-003

Matlab files available here: i2tmatlab.zip

How to choose the right values

FlexSEA boards such as FlexSEA-Rigid (used by Exo and ActPack) have a surface-mount fuse to protect the board and the user against extreme events. The maximum current supported by that fuse (typically 15A) is much higher than the maximum current needed for most wearable robotics applications. For a given application, aim to use the lowest current possible.

For example, if you know that your average current is 1A (pro tip: do a quick experiment and look at the average current in the logs) you may decide to pick 1.5A: enough margin to account for errors. If you backtrack your maximum torque to require 10A at the battery for 100ms, use 11A for 150ms.

These values will make the programmable fuse trip as soon as your system goes past those limits (control algorithm bug, stalled motor, etc.) When that happens, the circuit will turn off.

Pre-computed values (±30A sensor)

2.5A continuous, 15A for 1s, non-linearity at 22.5A:

I2C_SHIFT =     7.0000e+000 (7)
I2T_LEAK =   381.4697e+000 (381)
I2T_LIMIT =   133.5144e+003 (133514)
I2T_NON_LINEAR_THRESHOLD =   175.7812e+000 (176)

Time at given current (mA):
CURR =    25.0000e+003
time =   353.5354e-003
timeNL =    87.7193e-003

10A continuous, 15A for 1s, non-linearity at 20A:

I2C_SHIFT =    7.0000e+000 (7)
I2T_LEAK =     6.1035e+003 (6104)
I2T_LIMIT =    76.2939e+003 (76294)
I2T_NON_LINEAR_THRESHOLD =   156.2500e+000 (156)

Time at given current (mA):
CURR =    25.0000e+003
time =   238.0952e-003
timeNL =    22.6244e-003

Tips & Examples

The examples below are based on a Pocket board with a ±5A sensor, 1.5A continuous and 5A 500ms limit.

Program these values in i2t-current-limit.h:
============================================
I2C_SCALE_DOWN_SHIFT =     5.0000e+000
I2T_LEAK =     2.1973e+003
I2T_LIMIT =   111.0840e+003
I2T_WARNING =    88.8672e+003
Time at 1.6A:
time =    36.6935e+000
  • The standby current gets added to the load current. On a 30A board that's negligible, but on a ±5A board with a low limit that can be significant. As you can see, adding 100mA to the 1.5A load will make the protection trip after 37s instead of infinity.
  • Why does my board turn off with 1A for 900ms and 5A for 100ms? 1²*0.9 + 5²*0.1 = 0.9 + 2.5 = 3.4, sqrt(3.4) = 1.84A DC. Just the pulse is equivalent to 1.58A DC, enough to kill it.
  • How long do I need to wait between 5A 500ms pulses (assuming 0A the rest of the time)? 25*0.5 = 12.5, and our limit is 1.5. 1.5/12.5 = 12% duty cycle, so you need to wait at least 4.17s (0.5s/0.12) before the next pulse.
i2t.txt · Last modified: 2021/03/25 12:53 by jfduval