Files
Mapo-IOB-WIN/IOB-WIN-NEXT/IobSiemensPressoilCei.cs
T

274 lines
11 KiB
C#
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
using MapoSDK;
using System;
using System.Collections.Generic;
namespace IOB_WIN_NEXT
{
/// <summary>
/// Controllo Siemens specifico x impianti Pressoil+Cei (Pressa idraulica Valvital)
/// </summary>
public class IobSiemensPressoilCei : IobSiemens
{
/* --------------------------------------------------------------------------------
* Controlli SIEMENS CEI PRESSOIL (impianti ad induzione in VALVITAL)
* - basasto su SIEMENS
* - S7 vers 1500
*
* STRUTTURA MEMORIA DB64 READ e DB67 WRITE, vedere file conf json
* -------------------------------------------------------------------------------- */
#region Protected Fields
protected int counterMes2Plc = 0;
protected int counterPlc2Mes = 0;
protected DateTime lastPLCWatchDog;
#endregion Protected Fields
#region Public Constructors
/// <summary>
/// Classe base con i metodi x Siemens
/// </summary>
/// <param name="caller"></param>
/// <param name="adpConf"></param>
public IobSiemensPressoilCei(AdapterForm caller, IobConfiguration IOBConf) : base(caller, IOBConf)
{
lgInfo("NEW IOB SIEMENS versione PRESSOIL - CEI");
}
#endregion Public Constructors
#region Protected Methods
/// <summary>
/// Effettua decodifica aree memoria alla bitmap usata x MAPO
/// </summary>
protected override void decodeToBaseBitmap()
{
// init a zero...
B_input = 0;
/* -----------------------------------------------------
* bitmap MAPO STANDARD
* B0: POWER_ON
* B1: RUN
* B2: pzCount
* B3: allarme
* B4: manuale
* B5: emergenza
*
*
* - BIT di stato
* - DBX0.0 - Life bit
* - DBX0.1 Macchina lavora
* - DBX0.2 Macchina in ciclo
* - DBX0.3 Macchina in manuale
* - DBX0.4 Macchina in allarme
* - DBX0.5 Macchina in emergenza
*
----------------------------------------------------- */
byte mainData = RawInput[0];
int byteSignals = 0;
// bit 0 (poweron) imposto a 1 SE connected...
if (currPLC.IsConnected)
{
byteSignals += (1 << 0);
}
// RUN se lavora ed in ciclo
if ((mainData & (1 << 1)) != 0 && (mainData & (1 << 2)) != 0)
{
byteSignals += (1 << 1);
}
// manuale
if ((mainData & (1 << 3)) != 0)
{
byteSignals += (1 << 4);
}
// allarme
if ((mainData & (1 << 4)) != 0)
{
byteSignals += (1 << 3);
}
// emergenza
if ((mainData & (1 << 5)) != 0)
{
byteSignals += (1 << 5);
}
// salvo!
B_input = byteSignals;
// log opzionale!
if (verboseLog)
{
lgInfo($"Trasformazione dati: RawInput:{RawInput[0]} --> B_input: {B_input}");
}
}
#endregion Protected Methods
#region Public Methods
/// <summary>
/// Processo i task richiesti e li elimino dalla coda 1:1
/// </summary>
/// <param name="task2exe"></param>
public override Dictionary<string, string> executeTasks(Dictionary<string, string> task2exe)
{
// Verificare il protocollo: dovrebeb togliere SOLO i task eseguiti...
Dictionary<string, string> taskDone = new Dictionary<string, string>();
bool taskOk = false;
string taskVal = "";
// inizio con 1 byte di default
byte[] MemBlock = new byte[1];
string memAddrWrite = "";
if (task2exe != null)
{
// cerco task specifici
foreach (var item in task2exe)
{
taskOk = false;
taskVal = "";
// converto richiesta in enum...
taskType tName = taskType.nihil;
Enum.TryParse(item.Key, out tName);
// controllo sulla KEY
switch (tName)
{
case taskType.nihil:
case taskType.fixStopSetup:
case taskType.forceResetPzCount:
case taskType.forceSetPzCount:
case taskType.setProg:
taskVal = $"taskReq: {tName} | key: {item.Key} | val: {item.Value} | SKIPPED | NO EXEC";
break;
case taskType.setArt:
case taskType.setComm:
case taskType.setPzComm:
saveProdData(item);
// verifico se posso aggiornare valori in memoria...
if (memMap != null && memMap.mMapWrite != null)
{
if (memMap.mMapWrite.ContainsKey(item.Key))
{
dataConf currMem = memMap.mMapWrite[item.Key];
string addr = currMem.memAddr;
taskVal = $"SET task: {item.Key} --> {item.Value} | mem: {currMem.memAddr} - {currMem.size} byte";
// salvo il nuovo valore nella memoria... così prox invio lo trasmetterà
memMap.mMapWrite[item.Key].value = item.Value;
}
else
{
taskVal = $"NO DATA MEM, SET task: {item.Key} --> {item.Value}";
}
}
else
{
taskVal = $"NO MemMap found, SET task: {item.Key} --> {item.Value}";
}
int byteSize = 0;
// recupero dati da memMap... altrimenti NULLA
if (memMap.mMapWrite.ContainsKey(item.Key))
{
dataConf currMem = memMap.mMapWrite[item.Key];
byteSize = currMem.size;
memAddrWrite = currMem.memAddr;
MemBlock = new byte[byteSize];
if (currMem.tipoMem == plcDataType.String)
{
saveStringOnMemBlock(ref MemBlock, item.Key, 0, byteSize);
}
else if (currMem.tipoMem == plcDataType.Int)
{
short valDInt = 0;
short.TryParse(item.Value, out valDInt);
MemBlock = S7.Net.Types.Int.ToByteArray(valDInt);
}
else if (currMem.tipoMem == plcDataType.DInt)
{
int valDInt = 0;
int.TryParse(item.Value, out valDInt);
MemBlock = S7.Net.Types.DInt.ToByteArray(valDInt);
}
else if (currMem.tipoMem == plcDataType.Word)
{
ushort valDInt = 0;
ushort.TryParse(item.Value, out valDInt);
MemBlock = S7.Net.Types.Word.ToByteArray(valDInt);
}
else if (currMem.tipoMem == plcDataType.DWord)
{
uint valDInt = 0;
uint.TryParse(item.Value, out valDInt);
MemBlock = S7.Net.Types.DWord.ToByteArray(valDInt);
}
}
taskVal = item.Value;
break;
case taskType.sendWatchDogMes2Plc:
// processo scrittura BIT su DB67.DBX0.0
MemBlock = new byte[1];
memAddrWrite = "DB67.DBB0";
// compogo in byte... primo bit è setup/run, ultimo è watchdog
int valore = inSetup ? 1 : 0;
valore += (byte)(counterMes2Plc << 7);
MemBlock[0] = (byte)valore;
taskVal = $"VALUE DB67.0 --> {valore} | counter interno {counterMes2Plc}";
break;
case taskType.setParameter:
// richiedo da URL i parametri WRITE da popolare
lgInfo("Chiamata processMemWriteRequests");
taskVal = processMemWriteRequests();
// se restituiscce "" faccio altra prova...
if (string.IsNullOrEmpty(taskVal))
{
// i parametri me li aspetto come stringa composta paramName|paramvalue
if (item.Value.Contains("|"))
{
string[] paramsJob = item.Value.Split('|');
taskVal = $"REQUEST SET PARAMETERS: {paramsJob[0]} --> {paramsJob[1]}";
}
else
{
taskVal = $"WRONG REQUEST FOR SET PARAMETERS: {item.Value} doesnt contain pipe for splitting key/value";
}
}
break;
case taskType.startSetup:
// salvo che SONO IN SETUP!
inSetup = true;
break;
case taskType.stopSetup:
// salvo che SONO FUORI DAL SETUP!
inSetup = false;
break;
default:
taskVal = "SKIPPED | NO EXEC";
break;
}
// aggiungo task!
taskDone.Add(item.Key, taskVal);
// scrivo comunque!
taskOk = S7WriteBB(ref MemBlock, memAddrWrite);
if (!taskOk)
{
lgError($"Errore in S7WriteBB durante executeTasks: {item.Key} | {item.Value}");
}
}
}
return taskDone;
}
#endregion Public Methods
}
}