Commit 774b1787 authored by Jeroen Vreeken's avatar Jeroen Vreeken
Browse files

First batch of fixes and improvements from the Vitsch Electronics CVS

Mostly ethercat related in the ec directory.
parent 76442db3
......@@ -88,7 +88,7 @@ do { \
/* endif __x86_64__ */
#elif defined(__i386__)
#elif defined(__i386__) || (defined(__arm__) && !defined(__ARM_EABI__))
......
dt_ctrl
dt_ctrl.dot
dt_ctrl.pdf
*.dot
*.pdf
......@@ -27,6 +27,7 @@ BLOCKSRCS= \
block_or4.c \
block_pid.c \
block_pid_aw.c \
block_quadrature_decoder.c \
block_quantize.c \
block_random.c \
block_register.c \
......
/*
* Copyright (c) 2012,
* Daan Vreeken <Daan @ Vitsch . nl> - Vitsch Electronics
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
*
* THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS `AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT,
* INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
* (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
* SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
* CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*/
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include "controller_block.h"
#include "log.h"
/*
quadrature_decoder
input output
name name
----------------------------------------------
---| i |----
---| q pos |----
---| home |----
----------------------------------------------
Omschrijving:
Dit blokje kan worden gebruikt om het signaal van twee 90-graden verschoven
sensoren om te zetten in een encoder positie. De 'home' ingang kan optioneel
gebruikt worden om de positie op 0 te zetten.
De waarde van 'pos' wordt bij iedere opgaande flank van 'home' op 0 gezet.
Iedere verandering van de i- of q-ingang geeft een positie-verandering. Na
een heel rondje van 360 graden over [q, i] is 'pos' dus 4 hoger (of lager).
Dit is dus een 'flankenteller' en geen 'rondjes teller'.
*/
struct controller_block_private {
// ingangen
bool *i, *q;
bool *home;
// uitgangen
int32_t pos;
// interne variabelen
int last_iq;
bool last_home;
};
// een paar definities voor de leesbaarheid van de code
#define OUTPUT(name) (block->private->name)
#define INPUT(name) (*block->private->name)
#define VAR(name) (block->private->name)
#define I_LOW (0 << 0)
#define I_HIGH (1 << 0)
#define Q_LOW (0 << 1)
#define Q_HIGH (1 << 1)
// truth table to translate current state + next state => increment
static int increment_lut[4][4] = {
[I_LOW | Q_LOW] = {
[I_LOW | Q_LOW] = 0, // no motion
[I_HIGH | Q_LOW] = +1, // CW
[I_LOW | Q_HIGH] = -1, // CCW
[I_HIGH | Q_HIGH] = 0, // 180 degrees..!?
},
[I_HIGH | Q_LOW] = {
[I_LOW | Q_LOW] = -1,
[I_HIGH | Q_LOW] = 0,
[I_LOW | Q_HIGH] = 0,
[I_HIGH | Q_HIGH] = +1,
},
[I_LOW | Q_HIGH] = {
[I_LOW | Q_LOW] = +1,
[I_HIGH | Q_LOW] = 0,
[I_LOW | Q_HIGH] = 0,
[I_HIGH | Q_HIGH] = -1,
},
[I_HIGH | Q_HIGH] = {
[I_LOW | Q_LOW] = 0,
[I_HIGH | Q_LOW] = -1,
[I_LOW | Q_HIGH] = +1,
[I_HIGH | Q_HIGH] = 0,
},
};
static void calculate(struct controller_block *block)
{
int iq;
int increment;
iq = (INPUT(i) ? I_HIGH : I_LOW) |
(INPUT(q) ? Q_HIGH : Q_LOW);
increment = increment_lut[VAR(last_iq)][iq];
if ((INPUT(home) == true) && (VAR(last_home) == false)) {
// rising edge on 'home' input
if (OUTPUT(pos) != 0) {
log_send(LOG_T_DEBUG, "homing @ %d\n", OUTPUT(pos));
}
OUTPUT(pos) = 0;
} else {
// add increment to position
OUTPUT(pos) += increment;
}
// printf("i=%d q=%d\n", INPUT(i), INPUT(q));
// printf("enc: pos=%d increment=%d iq=%x last=%x\n",
// OUTPUT(pos), increment, iq, VAR(last_iq));
VAR(last_iq) = iq;
VAR(last_home) = INPUT(home);
}
static struct controller_block_interm_list interms[] = {
{ "i", CONTROLLER_BLOCK_TERM_BOOL, offsetof(struct controller_block_private, i) },
{ "q", CONTROLLER_BLOCK_TERM_BOOL, offsetof(struct controller_block_private, q) },
{ "home", CONTROLLER_BLOCK_TERM_BOOL, offsetof(struct controller_block_private, home) },
{ NULL },
};
static struct controller_block_outterm_list outterms[] = {
{ "pos", CONTROLLER_BLOCK_TERM_SINT32, offsetof(struct controller_block_private, pos) },
{ NULL },
};
struct controller_block * block_quadrature_decoder_create(char *name)
{
struct controller_block *block;
block = controller_block_alloc("quadrature_decoder", name,
sizeof(struct controller_block_private));
if (block == NULL)
return NULL;
if (controller_block_interm_list_init(block, interms))
goto err_block;
if (controller_block_outterm_list_init(block, outterms))
goto err_block;
block->calculate = calculate;
// this block doesn't have any parameters
block->param_get = NULL;
block->param_set = NULL;
// initial state
VAR(last_iq) = I_LOW | Q_LOW;
VAR(last_home) = false;
OUTPUT(pos) = 0;
controller_block_add(block);
return block;
err_block:
controller_block_free(block);
return NULL;
}
......@@ -797,3 +797,49 @@ int controller_block_outterm_list_init(struct controller_block *block,
return 0;
}
/* Helper function to create a new block */
struct controller_block *controller_block_alloc(char *type, char *name,
size_t private_size)
{
struct controller_block *blk;
blk = calloc(1, sizeof(struct controller_block));
if (!blk)
goto err_calloc;
blk->type = type;
blk->name = strdup(name);
if (!blk->name)
goto err_name;
if (private_size > 0) {
blk->private = calloc(1, private_size);
if (!blk->private)
goto err_private;
}
return blk;
err_private:
free(blk->name);
err_name:
free(blk);
err_calloc:
return NULL;
}
void controller_block_free(struct controller_block *blk)
{
if (blk->name)
free(blk->name);
if (blk->private)
free(blk->private);
if (blk->input)
free(blk->input);
if (blk->output)
free(blk->output);
free(blk);
}
......@@ -221,6 +221,12 @@ void controller_block_param_handle(void);
char *controller_block_context_get(void);
void controller_block_context_set(char *new_context);
/* Helper function to create a new block */
struct controller_block *controller_block_alloc(char *type, char *name,
size_t private_size);
void controller_block_free(struct controller_block *blk);
#define RPM2RADS(val) ((val)*2.0*M_PI/60.0)
#define RADS2RPM(val) ((val)*60.0/(2.0*M_PI))
#define DEG2RAD(val) ((val)*2.0*M_PI/360.0)
......
......@@ -55,7 +55,6 @@ void il2c_program(char *program)
fprintf(il2c_cout, "#include <stdio.h>\n");
fprintf(il2c_cout, "#include <stdlib.h>\n");
fprintf(il2c_cout, "#include <string.h>\n");
fprintf(il2c_cout, "#include <malloc.h>\n");
fprintf(il2c_cout, "#include <math.h>\n");
fprintf(il2c_cout, "#include <controller/controller_block.h>\n");
fprintf(il2c_cout, "\n");
......@@ -781,14 +780,8 @@ void il2c_block_body(void)
fprintf(il2c_cout, "{\n");
fprintf(il2c_cout, "\tstruct controller_block *block;\n");
fprintf(il2c_cout, "\n");
fprintf(il2c_cout, "\tif (!(block = malloc(sizeof(struct controller_block))))\n");
fprintf(il2c_cout, "\t\treturn NULL;\n");
fprintf(il2c_cout, "\n");
fprintf(il2c_cout, "\tblock->type = \"%s\";\n", il2c_blockname);
fprintf(il2c_cout, "\tif (!(block->name = strdup(name)))\n");
fprintf(il2c_cout, "\t\treturn NULL;\n");
fprintf(il2c_cout, "\n");
fprintf(il2c_cout, "\tif (!(block->private = malloc(sizeof(struct controller_block_private))))\n");
fprintf(il2c_cout, "\tif (!(block = controller_block_alloc(\"%s\", name, sizeof(struct controller_block_private))))\n",
il2c_blockname);
fprintf(il2c_cout, "\t\treturn NULL;\n");
fprintf(il2c_cout, "\n");
......
......@@ -17,6 +17,8 @@
*/
#define _GNU_SOURCE
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
......@@ -60,6 +62,9 @@ int sample_timing(char *args, char *out, int *outlen)
int main(int argc, char **argv)
{
char *ctrl_filename;
char *dot_filename;
controller_block_param_init();
if (argc < 2) {
......@@ -69,19 +74,20 @@ int main(int argc, char **argv)
return 1;
}
ctrl_filename = argv[1];
/* Create and link blocks */
if (controller_load(argv[1])) {
if (controller_load(ctrl_filename)) {
printf("Could load controller file\n");
return 1;
}
controller_trace_server_start(CTRL_TRACE_PORT, 100);
/* Start command shell */
shell_cmd_add(&(struct shell_cmd){"timing", "reset/print sample timing", sample_timing });
shell_cmd_add(&(struct shell_cmd){"timing", "reset/print sample timing", sample_timing });
controller_load_shell_add();
......@@ -92,7 +98,9 @@ int main(int argc, char **argv)
log_server_start(CTRL_LOG_PORT);
controller_dumpdot("dt_ctrl.dot");
asprintf(&dot_filename, "%s.dot", ctrl_filename);
controller_dumpdot(dot_filename);
free(dot_filename);
/* Start 'sample' */
......
OS= $(shell uname -s)
CFLAGS= -Wall -O3 \
-I. -I.. -I../log -I../controller
LDFLAGS= -lpthread -lrt -ldl -lm -L../lib
LDFLAGS= -lpthread -lrt -lm -L../lib
ifneq ($(OS), FreeBSD)
LDFLAGS+= -ldl
endif
LIBSRCS= ec.c esc.c canopen.c ec_stoeber.c block_ec.c eth_linux.c
ifeq ($(OS), FreeBSD)
LIBSRCS+= eth_bsd.c
else
LIBSRCS+= eth_linux.c
endif
LIBSRCS= ec.c esc.c canopen.c ec_stoeber.c block_ec.c
LIBOBJS= $(LIBSRCS:.c=.lo)
BLOCKSRCS= \
......@@ -14,6 +28,7 @@ BLOCKSRCS= \
block_beckhoff_el4xxx.c \
block_beckhoff_el5001.c \
block_beckhoff_el5101.c \
block_beckhoff_el7031.c \
block_stoeber.c
BLOCKS=$(BLOCKSRCS:.c=.lo)
......
/*
Copyright Jeroen Vreeken (pe1rxq@amsat.org), 2009, 2011
Copyright Stichting C.A. Muller Radioastronomiestation, 2009, 2011
Copyright Daan Vreeken <Daan@Vitsch.nl> - Vitsch Electronics, 2010
This program is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
......@@ -17,7 +18,6 @@
*/
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
......@@ -26,6 +26,7 @@
#include "block_beckhoff_el1xxx.h"
#include "ec.h"
#include "esc.h"
#include "log.h"
struct controller_block_private {
bool input1;
......@@ -83,32 +84,59 @@ struct beckhoff_el1xxx_type {
char *name;
uint32_t productcode;
int inputs;
struct controller_block_outterm_list *outterms;
};
static struct controller_block_outterm_list outterms_2[] = {
{ "input1", CONTROLLER_BLOCK_TERM_BOOL, offsetof(struct controller_block_private, input1) },
{ "input2", CONTROLLER_BLOCK_TERM_BOOL, offsetof(struct controller_block_private, input2) },
{ NULL },
};
static struct controller_block_outterm_list outterms_4[] = {
{ "input1", CONTROLLER_BLOCK_TERM_BOOL, offsetof(struct controller_block_private, input1) },
{ "input2", CONTROLLER_BLOCK_TERM_BOOL, offsetof(struct controller_block_private, input2) },
{ "input3", CONTROLLER_BLOCK_TERM_BOOL, offsetof(struct controller_block_private, input3) },
{ "input4", CONTROLLER_BLOCK_TERM_BOOL, offsetof(struct controller_block_private, input4) },
{ NULL },
};
static struct controller_block_outterm_list outterms_8[] = {
{ "input1", CONTROLLER_BLOCK_TERM_BOOL, offsetof(struct controller_block_private, input1) },
{ "input2", CONTROLLER_BLOCK_TERM_BOOL, offsetof(struct controller_block_private, input2) },
{ "input3", CONTROLLER_BLOCK_TERM_BOOL, offsetof(struct controller_block_private, input3) },
{ "input4", CONTROLLER_BLOCK_TERM_BOOL, offsetof(struct controller_block_private, input4) },
{ "input5", CONTROLLER_BLOCK_TERM_BOOL, offsetof(struct controller_block_private, input5) },
{ "input6", CONTROLLER_BLOCK_TERM_BOOL, offsetof(struct controller_block_private, input6) },
{ "input7", CONTROLLER_BLOCK_TERM_BOOL, offsetof(struct controller_block_private, input7) },
{ "input8", CONTROLLER_BLOCK_TERM_BOOL, offsetof(struct controller_block_private, input8) },
{ NULL },
};
static struct beckhoff_el1xxx_type devlist[] = {
{ "EL1002", ESC_ESI_PRODUCTCODE_BECKHOFF_EL1002, 2 },
{ "EL1004", ESC_ESI_PRODUCTCODE_BECKHOFF_EL1004, 4 },
{ "EL1008", ESC_ESI_PRODUCTCODE_BECKHOFF_EL1008, 8 },
{ "EL1012", ESC_ESI_PRODUCTCODE_BECKHOFF_EL1012, 2 },
{ "EL1014", ESC_ESI_PRODUCTCODE_BECKHOFF_EL1014, 4 },
{ "EL1018", ESC_ESI_PRODUCTCODE_BECKHOFF_EL1018, 8 },
{ "EL1024", ESC_ESI_PRODUCTCODE_BECKHOFF_EL1024, 4 },
{ "EL1034", ESC_ESI_PRODUCTCODE_BECKHOFF_EL1034, 4 },
{ "EL1084", ESC_ESI_PRODUCTCODE_BECKHOFF_EL1084, 4 },
{ "EL1088", ESC_ESI_PRODUCTCODE_BECKHOFF_EL1088, 8 },
{ "EL1094", ESC_ESI_PRODUCTCODE_BECKHOFF_EL1094, 4 },
{ "EL1098", ESC_ESI_PRODUCTCODE_BECKHOFF_EL1098, 8 },
{ "EL1104", ESC_ESI_PRODUCTCODE_BECKHOFF_EL1104, 4 },
{ "EL1114", ESC_ESI_PRODUCTCODE_BECKHOFF_EL1114, 4 },
{ "EL1124", ESC_ESI_PRODUCTCODE_BECKHOFF_EL1124, 4 },
{ "EL1134", ESC_ESI_PRODUCTCODE_BECKHOFF_EL1134, 4 },
{ "EL1144", ESC_ESI_PRODUCTCODE_BECKHOFF_EL1144, 4 },
{ "EL1202", ESC_ESI_PRODUCTCODE_BECKHOFF_EL1202, 2 },
{ "EL1252", ESC_ESI_PRODUCTCODE_BECKHOFF_EL1252, 2 },
{ "EL1262", ESC_ESI_PRODUCTCODE_BECKHOFF_EL1262, 2 },
{ "EL1702", ESC_ESI_PRODUCTCODE_BECKHOFF_EL1702, 2 },
{ "EL1712", ESC_ESI_PRODUCTCODE_BECKHOFF_EL1712, 2 },
{ "EL1722", ESC_ESI_PRODUCTCODE_BECKHOFF_EL1722, 2 },
{ "EL1002", ESC_ESI_PRODUCTCODE_BECKHOFF_EL1002, 2, outterms_2 },
{ "EL1004", ESC_ESI_PRODUCTCODE_BECKHOFF_EL1004, 4, outterms_4 },
{ "EL1008", ESC_ESI_PRODUCTCODE_BECKHOFF_EL1008, 8, outterms_8 },
{ "EL1012", ESC_ESI_PRODUCTCODE_BECKHOFF_EL1012, 2, outterms_2 },
{ "EL1014", ESC_ESI_PRODUCTCODE_BECKHOFF_EL1014, 4, outterms_4 },
{ "EL1018", ESC_ESI_PRODUCTCODE_BECKHOFF_EL1018, 8, outterms_8 },
{ "EL1024", ESC_ESI_PRODUCTCODE_BECKHOFF_EL1024, 4, outterms_4 },
{ "EL1034", ESC_ESI_PRODUCTCODE_BECKHOFF_EL1034, 4, outterms_4 },
{ "EL1084", ESC_ESI_PRODUCTCODE_BECKHOFF_EL1084, 4, outterms_4 },
{ "EL1088", ESC_ESI_PRODUCTCODE_BECKHOFF_EL1088, 8, outterms_8 },
{ "EL1094", ESC_ESI_PRODUCTCODE_BECKHOFF_EL1094, 4, outterms_4 },
{ "EL1098", ESC_ESI_PRODUCTCODE_BECKHOFF_EL1098, 8, outterms_8 },
{ "EL1104", ESC_ESI_PRODUCTCODE_BECKHOFF_EL1104, 4, outterms_4 },
{ "EL1114", ESC_ESI_PRODUCTCODE_BECKHOFF_EL1114, 4, outterms_4 },
{ "EL1124", ESC_ESI_PRODUCTCODE_BECKHOFF_EL1124, 4, outterms_4 },
{ "EL1134", ESC_ESI_PRODUCTCODE_BECKHOFF_EL1134, 4, outterms_4 },
{ "EL1144", ESC_ESI_PRODUCTCODE_BECKHOFF_EL1144, 4, outterms_4 },
{ "EL1202", ESC_ESI_PRODUCTCODE_BECKHOFF_EL1202, 2, outterms_2 },
{ "EL1252", ESC_ESI_PRODUCTCODE_BECKHOFF_EL1252, 2, outterms_2 },
{ "EL1262", ESC_ESI_PRODUCTCODE_BECKHOFF_EL1262, 2, outterms_2 },
{ "EL1702", ESC_ESI_PRODUCTCODE_BECKHOFF_EL1702, 2, outterms_2 },
{ "EL1712", ESC_ESI_PRODUCTCODE_BECKHOFF_EL1712, 2, outterms_2 },
{ "EL1722", ESC_ESI_PRODUCTCODE_BECKHOFF_EL1722, 2, outterms_2 },
};
struct controller_block * block_beckhoff_el1xxx_create(char *name, va_list ap)
......@@ -123,6 +151,7 @@ struct controller_block * block_beckhoff_el1xxx_create(char *name, va_list ap)
char *eltype;
int devno;
bool sim = !ec_initialized();
struct timespec timeout = { 1, 0 };
eltype = va_arg(ap, char *);
devno = va_arg(ap, int);
......@@ -134,7 +163,7 @@ struct controller_block * block_beckhoff_el1xxx_create(char *name, va_list ap)
}
}
if (dev < 0)
return NULL;
goto err_ethercat;
if (!sim) {
slaves = ec_slave_count();
......@@ -155,21 +184,14 @@ struct controller_block * block_beckhoff_el1xxx_create(char *name, va_list ap)
}
}
if (!found) {
printf("Device not found\n");
return NULL;
log_send(LOG_T_ERROR, "%s: Device not found\n", name);
goto err_ethercat;
}
}
block = malloc(sizeof(struct controller_block));
if (!block)
return NULL;
block->private = calloc(sizeof(struct controller_block_private), 1);
if (!block->private)
return NULL;
block->type = sim ? "beckhoff_el1xxx_sim" : "beckhoff_el1xxx";
block->name = strdup(name);
block = controller_block_alloc(
sim ? "beckhoff_el1xxx_sim" : "beckhoff_el1xxx",
name, sizeof(struct controller_block_private));
if (!sim) {
esc_init(&addr);
......@@ -180,54 +202,17 @@ struct controller_block * block_beckhoff_el1xxx_create(char *name, va_list ap)
esc_pdo_rx_set(&addr, &pdo_rx, &block->private->rx_buffer);
if (esc_al_state_set(&addr, ESC_AL_STATE_INIT) < 0)
printf("Could not go to state init\n");
if (esc_al_state_set(&addr, ESC_AL_STATE_PRE_OPERATIONAL) < 0)
printf("Could not go to state pre operational\n");
if (esc_al_state_set(&addr, ESC_AL_STATE_SAFE_OPERATIONAL) < 0)
printf("Could not go to state safe operational\n");
if (esc_al_state_set(&addr, ESC_AL_STATE_INIT, &timeout) < 0)
log_send(LOG_T_ERROR, "Could not go to state init\n");
if (esc_al_state_set(&addr, ESC_AL_STATE_PRE_OPERATIONAL, &timeout) < 0)
log_send(LOG_T_ERROR, "Could not go to state pre operational\n");
if (esc_al_state_set(&addr, ESC_AL_STATE_SAFE_OPERATIONAL, &timeout) < 0)
log_send(LOG_T_ERROR, "Could not go to state safe operational\n");
}
block->inputs = 0;
block->input = NULL;
/* Inputs on the hardware are outputs on this software block */
block->outputs = devlist[dev].inputs;
block->output = malloc(sizeof(struct controller_block_outterm) * 8);
if (!block->output)
return NULL;
block->output[0].name = "input1";
block->output[0].type = CONTROLLER_BLOCK_TERM_BOOL;
block->output[0].value.b = &block->private->input1;
block->output[0].source = block;
block->output[1].name = "input2";
block->output[1].type = CONTROLLER_BLOCK_TERM_BOOL;
block->output[1].value.b = &block->private->input2;
block->output[1].source = block;
block->output[2].name = "input3";
block->output[2].type = CONTROLLER_BLOCK_TERM_BOOL;
block->output[2].value.b = &block->private->input3;
block->output[2].source = block;
block->output[3].name = "input4";
block->output[3].type = CONTROLLER_BLOCK_TERM_BOOL;
block->output[3].value.b = &block->private->input4;
block->output[3].source = block;
block->output[4].name = "input5";
block->output[4].type = CONTROLLER_BLOCK_TERM_BOOL;
block->output[4].value.b = &block->private->input5;
block->output[4].source = block;
block->output[5].name = "input6";
block->output[5].type = CONTROLLER_BLOCK_TERM_BOOL;
block->output[5].value.b = &block->private->input6;
block->output[5].source = block;
block->output[6].name = "input7";
block->output[6].type = CONTROLLER_BLOCK_TERM_BOOL;
block->output[6].value.b = &block->private->input7;
block->output[6].source = block;
block->output[7].name = "input8";
block->output[7].type = CONTROLLER_BLOCK_TERM_BOOL;
block->output[7].value.b = &block->private->input8;
block->output[7].source = block;
if (controller_block_outterm_list_init(block, devlist[dev].outterms))
goto err_outputs;
switch (devlist[dev].inputs) {
case 2:
......@@ -243,11 +228,11 @@ struct controller_block * block_beckhoff_el1xxx_create(char *name, va_list ap)
if (sim)
block->calculate = NULL;
block->params = 0;
block->param = NULL;