Vai al contenuto
PLC Forum


Routine Allarmi - Generare anche 1000 allarmi


rddiego

Messaggi consigliati

Buongiorno a tutti, oggi sarei lieto di ricevere un qualche consiglio riguardo a come generare un numero x di allarmi di un qualsiasi impianto.

Le condizioni sono le seguenti:

- tutti gli allarmi devono poter essere temporizzati

- tutti gli allarmi devono essere autoritenuti fino alla pressione del reset allarmi (se sparita la condizione di allarme)

Diciamo che l'allarme standard che vorrei ottenere sia descritto come segue:

IF "condizione d'allarme" START "tempo di ritardo"

IF "tempo ritardo" THEN "attivazione allarme"

IF "attivazione allarme" OR ("allarme" AND NOT "reset") THEN "allarme"

Con Premium Telemecanique è tranquillamente indicizzabile il tutto e con uno splendido FOR/NEXT è risolto in 5 righe. Ho provato a tradurre il tutto in AWL (non ho SCL), ma i risultati non mi soddisfano benchè funzioni abbastanza bene.

Il problema che ho riscontrato è il tempo ciclo : con molto meno di 200 allarmi indicizzati il plc va in watch-dog

Ho risolto smembrando tutti gli allarmi in più scansioni....

Vorrei arrivare a generare almeno 1000 allarmi in una scansione sola. 1000 allarmi sarebbero almeno 3000 righe d'istruzione + altre 1000 per generare "condizione d'allarme" + il resto del programma e quant'altro.. Insomma sarebbe bello comprimere tutta la parte degli allarmi.

Sono arrivato ad un punto in cui riesco a fare il tutto in più scansioni stando sotto il secondo che è la base tempo dei miei contatori. Inconveniente unico ma trascurabile (per determinate applicazioni) è l'intervento dell'allarme che se anche debba essere immediato, scatterebbe solo quando viene "scannato" il suo pacchetto. Non so se mi sono spiegato, ma non ha importanza il problema è il tempo di scansione.

Non ho bisogno delle singole istruzioni quanto più della filosofia... ho bisogno.... può essere utile a tutti.... a tutti... impianti con 1000 allarmi non sono molti... però pensate ad una centrale elettrica....

Link al commento
Condividi su altri siti


emanuele.croci

1) Potresti provare le istruzioni booleane sulle word che operano bit a bit, per farne 16 alla volta....

ALLARME = ALLARME OW CONDIZIONE AW RESETNEGATO (forse guadagni qualcosa).

Considerando che ad ogni operazione devi fare anche un indirizzamento indiretto per pescare l' ERRORE (X)...

[nota che per questo punto non so darti un'alternativa per il problema del timer, di ritardare CONDIZIONE...]

2) Inoltre è importante anche dove memorizzi i tuoi dati:

l'area MERKER è la più veloce (U M50.0, U M50.1, U M50.2)

l'area del DB corrente è 2a (AUF DB12 ..... U DBX50.0 U DBX50.1)

se ogni volta indichi il DB è più lento ancora (U DB12.DBX50.0... U DB12.DBX50.1).

Facci sapere!

Ciao, Emanuele

P.S.: scopro ora che esistono anche le istruzioni OD, XOD ecc.... , booleane sulle doppie word, per farne 32 alla volta!

Modificato: da emanuele.croci
Link al commento
Condividi su altri siti

Ciao rddiego

Ho scritto una routine di poche righe in AWL (per S7300/400) che potrebbe assolvere a parte della funzione che cerchi. Purtroppo non ho trovato un modo per temporizzare l'intervento di un singolo allarme (tu dirai: 'si grazie, così ero capace anch'io!', ma io riesco ad arrivare fin qui....)

Ti inserisco il codice che sicuramente sarai in grado di capire senza particolari spiegazioni.

      AUF "Allarmi"                      // DB degli Allarmi: vedi descrizione sotto

      L  32                                    // Valore arbitrario: è il numero di DoubleWord degli Allarmi. qui con 32 fai 1024 Allarmi

M001: T  #Loop_Cnt                    // Variabile temoranea definita nell'area dichiarazioni locali

      L  DBD [AR1,P#0.0]              // Stai caricando una doble di condizioni

      L  DBD [AR1,P#32.0]            // Stai caricando una double di appoggio delle condizioni (32 dipende dalla DB)

      XOD

      UD   

      T  DBD [AR1,P#64.0]            // Stai appoggiando il risultato nela double di destinazione

      L  DBD [AR1,P#0.0]

      T  DBD [AR1,P#32.0]            // Aggiornamento della double di appoggio

      +AR1  P#4.0                        // Aggiornamento del puntatore per il loop successivo

      L  #Loop_Cnt

      LOOP  M001

      UN "Reset"

      SPB  M002

      L      L#0

      T      DBD 64

      T      DBD 68

      T      DBD 72

      T      DBD 76

      ...

      ...

      ...

M002: NOP 0

Con un unico DB debitamente strutturato, puoi ottenere la gestione di 1024 allarmi con un loop di soli 32 steps.

La struttura del DB di questo programma è la seguente:

-32 DoubleWord che contengono i bit delle condizioni di Allarme (i risultati delle logiche che devono produrre l'Allarme)

-32 DoubleWord di appoggio (sono come gli appoggi per generare i fronti, il loro stato non è significativo)

-32 DoubleWord che contengono i bit di Allarme (queli che restano alti fino al Reset dell'Operatore)

Le tre distinte aree qui descritte devono essere contigue e in quest'ordine (per come è scritta la routine).

Il numero di elementi qui adottato (32) è arbitrario, può essere di qualunque dimensione a patto che tutte tre le aree (di ugual dimensione) possano essere contenute nello stesso DB.

N.B. La routine è scritta per lavorare con 32 doubleword. Se si vuole modificare questo valore, è necessario modificare anche la routine sostituendo il nuovo valore in tutte le ricorrenze del numero 32 e sostituire il numero 64 con il valore doppio del numero che si è deciso di adottare.

Spero ti possa interessare.

Ciao.

Link al commento
Condividi su altri siti

Non metto bene a fuoco il problema: con Premium gira bene e con Siemens no? Il riferimento all'AWL indica che hai migrato l'applicazione Telemecanique su Siemens?

Generalmente per questo genere di routine io lavoro almeno a word ed utilizzo la tecnica delle tabelle e dell'indirizzamento indiretto. Ovviamente ci vuole una sapiente allocazione delle variabili nel database. Con Omron utilizzo un'interessante funzione di data-search (non ricordo la sigla) che è molto veloce e mi restituisce al volo la posizione di dati che non soddisfano una condizione (per esempio CondizioneAllarme = 0). Sono certo d'aver gestito almeno 500 allarmi con tempi di ciclo nell'ordine dei 35-40 ms (nel programma c'era anche del resto). Non usavo Siemens però, che notoriamente sono piuttosto lentini. :(

Ciao.

Link al commento
Condividi su altri siti

dunque si creano diversi array di bit e interi ;quelli dei bit sono relativi alla generazione vera e proprio dell'allarme , all'autoritenuta .Mentre gli array di interi soddisferanno gli accumulatori di ogni relativo

"contatore di tempo" che sostituira il timer , poi i preset ect

generazione_allarme:array[1..100] of bool;

allarme: array[1..100] of bool;

preset: array[1..100] of int;

contatore:array[1..100] of int;

reset:bool;

in una FCx dedicata di vanno a generare gli allarmi , per esmpio

un E0.0

= generazione_allarme[1]

...

...

un E20.0

= generazione_allarme[100]

//poi settano i preset di tempo di ogni allarme

L 10

T preset[1]

....

poi si utilizza il fronte del merker di clock di un secondo , ed una istruzione for_next

realizzabile anche in awl con puntatori .

nel loop si va vedere se c'e' l'allarme generato , quindi si incrementa il relativo "contatore di tempo" sulla base di 1 secondo , e quando questo arriva ad essere >= del rispettivo preset (sempre indicizzato )

si alza il ripesttivo allarme indicizzato .

Questo a grandi linee ,poi col reset oppure l'acknoledge si possono gestire il riconoscimento e il reset di tutti gli allarmi

nella logica verranno utilizzati i bit allarme[indice] nei rispettivi blocchi di interlock

ciao

walter

Link al commento
Condividi su altri siti

Rispondo prima a Fransys.

Con premium 1000 allarmi indicizzati come spiegato li eseguo in un ciclo solo di 8ms.

Con s7400 un ciclo non basta. Per ora sono a 32 salti all'indietro per ciclo (come spiegato indicativamente da gramma) in 30-40 ms.

La stessa routine su s7300 va in watchdog e allora sono 16 salti all'indietro.

Sto preparando la stessa routine per plc 5 di AB ed andrò ad occhi chiusi con logix5000 che è superveloce.

L'intento è di avere una routine parametrizzabile (numero di allarmi) standard da utilizzare nei vari programmi con diversi plc. Siccome la parte allarmi è uno dei fondamenti di un programma, averlo già pronto non è male.

Link al commento
Condividi su altri siti

non usare plc s7 , non si possono permettere queste velocita

sono lenti come la fame , anche gli quelli di ultima generazione

non esiste una funzione come dici tu per plc Siemens.

Quindi in questi casi va progettata l'automazione e di conseguenza fatta una scelta di plc

che non e' godibile con i plc della siemens

Ok Allen Bradley , OK premium , ok altri , ma non siemens

e' come dire la solita battuta vecchia come il cucu :" ho una 500 e voglio viaggiare come una Ferrari"

IMPOSSIBILE!!!!

:)

Link al commento
Condividi su altri siti

Rispondo a Gramma. Ok hai tradotto alla perfezione il quesito posto. Solo che bisogna temporizzarli sti allarmi. Non userò di certo i Timer della cpu (non ne ho abbastanza comunque). Incrementerò dei byte (mi sembrano sufficienti 250 secondi max). Ho una FC di tre righe che mi fa questo. Questa FC parametrizzata è richiamata per ogni allarme con le condizioni attive. Ed ecco che al limite del possibile dovrei richiamare 1000 FC per scansione....

Link al commento
Condividi su altri siti

Prova un po' ad utilizzare gli fc standard FC10 E FC29 (confronto tra stringhe)

ed SFC20 block move.

confronti i 1000 bit con fc10 di allarmi con un'area di appoggio (merker va benissimo) come se fossero una stringa lunghissima, poi dopo il confronto prendi i tuoi bit e li copi (sfc20) nell'area di appoggio.

durante i confronti se hai delle differenze fai startare il timer che quando finisce di contare va a 1 (se) e con quel timer puoi abilitare gli allarmi.

spero di essere stato chiaro

Link al commento
Condividi su altri siti

Rispondo prima a Fransys.

E io? sono geloso!!! :(

Per Fransys: il lclock di sistema è asincrono alla scansione, potresti interrogarlo dopo 999ms come dopo 1ms dal'ultima commutazione. Così hai un'imprecisione sul ritardo della generazione degli allarmi anche di 1sec!

non usare plc s7 , non si possono permettere queste velocita

sono lenti come la fame , anche gli quelli di ultima generazione

non esiste una funzione come dici tu per plc Siemens.

Boh... Io non sono convinto... per me, se una routine di 1000 segmenti impiega 30-40ms ad essere eseguta su un 400, c'è qualcosa che non quadra.... Anche per un 300, 512 righe non sono molte, non mi sembra possibile che possa andare in watch-dog! Forse sbaglio io, ma sei sicuro di non avere del loop nidificati?

Ciao.

Link al commento
Condividi su altri siti

per gramma. Non mi piace il reset che hai fatto poichè se l'allarme è attivo ed ha le condizioni, premendo reset per un ciclo di scansione lo cancelli e non è bello.

Link al commento
Condividi su altri siti

no gramma. C'è il resto del programma.... ed in ogni caso la mia routine che differisce dalla tua di un niente gestisce anche i tempi di ritardo che è il nocciolo ma forse STEU mi ha indicato una buona strada ora ci rifletto..

Link al commento
Condividi su altri siti

Ok, hai ragione.

Ma basta spostare il Reset sopra la routine di generazione. Tutti gli allarmi vengono cancellati, quelli che sono ancora attivi vengono rigenerati immediatamente dopo.

Non credo riuscirai a chiamare un FC (o un SFC) 1000 volte...in questo modo sicuramente la CPU andrà in watchdog! piuttosto usa un byte con un cotrollo di valore raggiunto (preset di ritardo), poi vai ad incrementare tutti i byte attivati dai rispettivi allarmi (L Byte; +1; T Byte) in un unico FC che sarà richiamato a tempo (se vuoi anche in OB35) In questo modo 'costruisci' N timers utilizzando solo dei bytes

P.S. conviene fare anche il controllo di valore raggiunto nell'FC che fa l'incremento....

ciao.

Link al commento
Condividi su altri siti

neanche, non devo cancellarli tutti perchè sono temporizzati, così ripartirebbe il tempo di ritardo. Piuttosto anzichè azzerare le dword faccio l'AND dword

DWord condizioni

DWord allarmi

UW

T allarmi

Link al commento
Condividi su altri siti

Per Fransys: il lclock di sistema è asincrono alla scansione, potresti interrogarlo dopo 999ms come dopo 1ms dal'ultima commutazione. Così hai un'imprecisione sul ritardo della generazione degli allarmi anche di 1sec!

Siamo d'accordo, sono partito dal presupposto che per il ritardo di un allarme una precisione di un secondo sia più che sufficiente.

Ciao.

Link al commento
Condividi su altri siti

CIAO RAGAZZI HO VISTO LA VOSTRA DISCUSSIONE...ED è STATA MOLTO INTERESSANTE

MI PERMETTO DI DIRE LA MIA DAL LATO PRATICO .......A VALORE PURAMENTE SOGGETTIVO SENZA OFFENDERE NESSUNO.

PENSO CHE SE HO L'ESIGENZA DI MONITORARE 1000 ALLARMI L'IMPIANTO DEVE ESSERE ABBASTANZA CORPOSO E QUINDI DEDUCO CHE SI NECESSARIA L'UTILIZZO DI UNA SUPERVISIONE.........

A QUESTO PUNTO PERCHè FARE GESTIRE AL PLC TUTTA QUESTA MOLE DI ALLARMI......

AL PLC GLI FACCIO FARE L'OPERAIO E CIOè GLI FACCIO ALZARE IL BRACCIO QUANDO SUCCEDE QUALCHE ALLARME/EVENTO...

ALLA SUPERVISIONE FACCIO DECIDERE QUALI ALLARMI TEMPORIZZARE,QUALI RENDERE SONORI,QUALI CANCELLABILI,QUALI ALLARMI SONO FATALI E QUALI NON,ECCC

PENSO CHE COSì FACENDO MI TENGO LA CPU DEL PLC PER LA GESTIONE DEL PROCESSO E LO SCARICO DAI COMPITI DI INTERFACCIA UTENTE...

Link al commento
Condividi su altri siti

Ciao

Si Trentaluca,è vero. però qui si cercava di estrapolare una funzione 'standard' per la gestione degli allarmi che sia utilizzabile + o - in tutti i programmi, senza doversi preoccupare di quanti sono gli eventi. Il numero 1000 è solo così, per dire, per fare una funzione efficiente anche se mostruosamente caricata.

Secondo me, la teoria di far gestire alla suervisione tutti gli allarmi (intendo come priorità, ritardo, abilitazione al reset, psw varie, ecc) è corretta, il PLC è in manovale, non deve gestire, deve eseguire (senza nulla togliere a chi svolge lavori manuali!).

Però, scrivi in minuscolo, altrimenti sembra che gridi!

Ciao.

Link al commento
Condividi su altri siti

Ok ragazzi scusate per il maiuscolo non me ne sono neanche accorto....

Certo ho capito quale era il vostro intento e lo ammiro........

Io ho voluto solo dare un opinione basata sulla mia esperienza.....

Ciao a tutti e buon week

Link al commento
Condividi su altri siti

Gianmario Pedrani

Io non utilizzerei gli indici

ma farei una cosa di questo tipo

creerei un fbxx

in sit_all :bool

in clock :bool

in reset_all :bool

in tempo: int

in abb_tempo: bool

in_out : memoria_all :bool

U sit_all

spbn all1

u clock

fp fp_app

= fp_app1

u fp_app1

spbn tt

L tempo

L tempo

>=I

spb tt

L temp

L 1

+ I

T Temp

tt: nop 0

u(

L temp

L tempo

>= I

)

u sit_all

S memoria_all

all1: nop 0

u reset

r memoria_all

queste riughe di codice funzionano solo se si verifica un allarme altrimenti il sistema le salta recuperando in tempo macchina.

Io lo usato per fare più di 400 all ed il sistema non ne ha risentito, perche finchè non si verifica un alllarme il plc salta.

ora chiama questa funzione in un fb di istanza ed il gioco è fatto

ciao spero di essere stato chiaro.

se hai bisogno chiedi

;)

Link al commento
Condividi su altri siti

Evidentemente la Siemens non manda le stesse CPU a tutti

 
      OPN   "Alarm DB"
      L     DW#16#FFFFFFF0
      LAR1  
      LAR2  
      SET   
      R     Q      0.0
      R     Q      0.1
      JU    M001
M006: NOP   0
      L     #grid
      SLW   1
      T     #grid
      L     0
      <>I   
      JC    M002
M001: NOP   0
      L     1
      T     #grid
      +AR1  P#2.0
      TAR1  
      L     P#64.0      //Numero DBW da leggere
      >=I   
      BEC   
      L     0
      L     DBW [AR1,P#800.0]
      <>I   
      S     Q      0.0
      L     DBW [AR1,P#1000.0]
      XOW   
      TAK   
      AW    
      L     0
      <>I   
      S     Q      0.1
M002: NOP   0
      OPN   "Alarm DB"
      +AR2  P#2.0
      L     #grid
      L     DBW [AR1,P#0.0]
      AW    
      <>I   
      JC    M003
      L     #grid
      L     DBW [AR1,P#400.0]
      AW    
      ==I   
      JC    M003
      OPN   "Alarms enable time DB"
      L     DBW [AR2,P#0.0]
      OPN   "Alarms enable timer DB"
      L     DBW [AR2,P#0.0]
      <=I   
      JC    M004
      L     1
      +I    
      T     DBW [AR2,P#0.0]
      JU    M005
M003: NOP   0
      OPN   "Alarms enable timer DB"
      L     0
      T     DBW [AR2,P#0.0]
M005: NOP   0
      OPN   "Alarms delay timer DB"
      L     0
      T     DBW [AR2,P#0.0]
      OPN   "Alarm DB"
      L     #grid
      INVI  
      L     DBW [AR1,P#600.0]
      AW    
      T     DBW [AR1,P#600.0]
      L     #grid
      L     DBW [AR1,P#1000.0]
      AW    
      INVI  
      L     DBW [AR1,P#800.0]
      AW    
      T     DBW [AR1,P#800.0]
      JU    M006
M004: NOP   0
      OPN   "Alarm DB"
      L     #grid
      L     DBW [AR1,P#200.0]
      AW    
      <>I   
      JC    M005
      OPN   "Alarms delay time DB"
      L     DBW [AR2,P#0.0]
      OPN   "Alarms delay timer DB"
      L     DBW [AR2,P#0.0]
      <=I   
      JC    M007
      L     1
      +I    
      T     DBW [AR2,P#0.0]
      JU    M006
M007: NOP   0
      OPN   "Alarm DB"
      L     #grid
      L     DBW [AR1,P#600.0]
      OW    
      T     DBW [AR1,P#600.0]
      L     #grid
      L     DBW [AR1,P#800.0]
      OW    
      T     DBW [AR1,P#800.0]
      JU    M006

Uso questo FC per la maggior parte dei miei programmi, richiamato con un clock di un secondo.

Va abbinato a 5 DB.

Alarm DB bit di abilitazione (word 0-199), condizione (word 200-399), allarme (word 400-599), masheratura (word 600-799), visualizzazione (word 800-999), ack (word 1000-1199)

Alarm enable time imposto in ogni word un tempo di ritardo all'abilitazione allarmi (tempo X)

Alarm enable timer contatore relativo al ritardo sopra

Alarm delay time imposto in ogni word un tempo di ritardo all'allarme (tempo Y)

Alarm delay timer contatore relativo al ritardo sopra

Quando un allarme deve essere controllato abilito l'enable (Alarm DB)

Quando un allarme ha la condizione positiva abilito il condition (Alarm DB)

Trascorso il tempo X e Y mi si setta alarm e display se non presente mask

Alarm è legato a enable e condition se manca uno di questi o ho mask cade l'allarme

Se cade enable (es.impianto fermo) al successivo (enablle+condition=1) aspetto tempo X e Y

Se cade condition (impianto in funzione ma condizione rientrata) al successivo condition=1 aspetto solo tempo Y

Verso HMI mando display che rientra solo se rientrato alarm e fatto ack (Alarm DB) da hmi

Controllando gli stati degli allarmi, attivo 2 uscite, una per allarme sonoro (ogni nuovo evento non ack) ed una per allarme presente.

Questo FC impostato per la lettura di 64 word quindi 1008 allarmi impiega in una CPU 312C che ho qui in ufficio mediamente 30-31ms.

Spesso tutta questa impostazione non viene sfruttata completamente, se non esistono le condizioni di enable e condition separata basta attivarle in parallelo e tenere a zero il tempo di enable.

Alarm e display è una esasperazione, solo perchè un pannello o un pc se fosse "in palla" potrebbe perdere un allarme che rientra subito. Per contro un allarme (che non blocca l'impianto) in un impianto automatico deve poter essere gestito sul suo stato non sulla sua visualizzazione.

Le tue esigenze sono inferiori quindi:

puoi togliere la gestione della abilitazione

puoi togliera la gestione del riconoscimento

puoi togliere la gestione della mascheratura

Sconsiglierei vivamente la gestione degli allarmi da HMI, l'impianto potrebbe essere in funzione anche con PC "in crisi".

Se hai bisogno di ulteriori chiarimenti fammi sapere

Modificato: da NULL
Link al commento
Condividi su altri siti

Il codice di FabioS è molto simile a quanto faccio io su macchine Omron, a parte l'accesso ai dati che nelle mie applicazioni è un po' diverso perché come dicevo faccio lo scan dei bit d'allarme con una funzione specifica.

Ciao.

Link al commento
Condividi su altri siti

Crea un account o accedi per commentare

Devi essere un utente per poter lasciare un commento

Crea un account

Registrati per un nuovo account nella nostra comunità. è facile!

Registra un nuovo account

Accedi

Hai già un account? Accedi qui.

Accedi ora
×
×
  • Crea nuovo/a...