Sign in to follow this  
Followers 0
LordNelson

FINS/TCP using Java

14 posts in this topic

Hi everyone, I'm implementing a SCADA software using Java and I would like to use FINS/TCP comms so as to work between PC and PLC (CJ1M-CPU13-ETN in ETN-21 mode). I found Multiway software that helped me a lot to undersand how does it work (it works). I also read manual W421-E1-04, but I'm not able to make the read status memory command work... When I send the FINS FRAME SEND Command I always receive 0x03 error response. Otherwise, with FINS/UDP i have no problem, but it's not my goal. Please, can someone help me?? Here it is my sample code Any suggestions will be well received! Thank you! test.zip
1 person likes this

Share this post


Link to post
Share on other sites
Hi everyone, I found where my problem was. Just specifiy correct length of byte data! Thanks anyway! Sample code attached. test.zip
3 people like this

Share this post


Link to post
Share on other sites
Thanks for posting the information - I am sure it will help someone along the way.

Share this post


Link to post
Share on other sites
Hi guys, I have searched this topic for a lot time. I have only a question: How I can try this project? With a emulator of Omron that use FINS protocol? And when I write in cmd: " javac Main.java", it returns this error: "Cannot find class Listener". Why? I put the Listerner.java class down the main class, reload the command but I have this error: "Cannot load Main class." Please help me. Thanks.

Share this post


Link to post
Share on other sites
It's not clear whether you found a solution to your problem with the java compiler. Just in case, I'm posting what I've done to run it successfully. Follow the instructions below to run the java file: 1) Place both java files into the same folder. 2) Open each java file and delete the first line where it says: "package com.prova;" 3) Type "javac Listener.java" and hit enter to compile Listener. This will generate a file called Listener.class. 4) Type "javac Main.java" and hit enter to compile Main. This will generate a file called Main.class. 5) Type "java Main" and hit enter. This will start executing the program.

Share this post


Link to post
Share on other sites
Thanks, it works fine. I'm new in this kind of progrmmation. I want to know something about FINS protocol: In follow your code and create a my project and it is subdivided in: OmronFinsPacket.java that is a class than help me to create tcp_header (byte array - size = 16) ,fins_header (byte array - size = 10) and fins_cmd (byte array - size = 8)OmronFins.java that is the main class that contain some method ( connect,close, writeOmronFinsPacket, readOmronFinsPacket etc ) . In the main I create OmronFins object , call the method and write it into a serverSocket that it receive the OmronFinsPacket and re-send it to the client for control if i write correctly. But now I want to understand how can I test my program? And if i can use an emulator of PLC when i write to PLC OmronFinsPacket, what is the response of PLC ? Thanks.

Share this post


Link to post
Share on other sites
I have done a test in a factory. This is the packet that I send to PLC: 70 73 78 83 0 0 0 26 0 0 0 2 0 0 0 0 -128 0 2 0 0 0 0 -13 0 100 1 1 -126 0 -116 0 0 32 -> read word from word 140 to 172. This is the response of PLC: 70, 73, 78, 83, 0, 0, 0, 16, 0, 0, 0, 1, 0, 0, 0, 2, -128, 0, 2, 0, 0, 0, 0, 80 Can someone help me please? Thanks.

Share this post


Link to post
Share on other sites
The error code in the response is "2" (the value before -128). 70, 73, 78, 83, 0, 0, 0, 16, 0, 0, 0, 1, 0, 0, 0, 2, -128, 0, 2, 0, 0, 0, 0, 80 Error Code 2 : The data length is too long

Share this post


Link to post
Share on other sites
Mmmm...I have to change the packet that i send? I think that i have to send: header - length - cmd - errCode- node 70 73 78 83 0 0 0 12 0 0 0 2 0 0 0 0 0 0 0 80 Response PLC: header - length - cmd - errCode- node - server node 70 73 78 83 0 0 0 12 0 0 0 2 0 0 0 0 0 0 0 80 0 0 0 0 Now i can send the complete command like this: node 70 73 78 83 0 0 0 26 0 0 0 2 0 0 0 0 -128 0 2 0 0 0 0 -13 0 100 1 1 -126 0 -116 0 0 32 -> read word from word 140 to 172. Right ? Edited by NicolaAbcd

Share this post


Link to post
Share on other sites
No, you have to run the connect() function in java with the following: 70 73 78 83 0 0 0 12 0 0 0 0 0 0 0 0 0 0 0 80 (here I corrected error code 2 as 0. Also, assuming 80 is your PC's IP address node e.g. 192.168.0.80, in my case it's 200 or 0xC8 and my PLC is 10 or 0x0A) Then, send the command to read 32 words from D140. I ran the Main.java with my PLC and got the following result. It received 32 words from D140 correctly: run:Connected using IP: /192.168.0.200:50351 Port: 50351Listening...Send: 46494E53 0000000C 00000000 00000000 000000C8 Receive: 46494E53 00000010 00000001 00000000 000000C8 0000000A 00000000 00000000 00000000 00000000 Listening...Send: 46494E53 0000001A 00000002 00000000 Send: 80000200 0A0000C8 0064Send: 01018200 8C000020 Receive: 46494E53 00000056 00000002 00000000 C0000200 C800000A 00640101 00000000 00000000 00000005 Listening...Receive: 00000000 00000000 00000000 33320150 30305C5C 00000004 00E60A46 00740000 00000000 0A460000 Listening...Receive: 00000000 00000000 000D0000 00000000 00000000 00000000 00000000 00000000 00000000 00000000 Listening...
1 person likes this

Share this post


Link to post
Share on other sites
Ok good. Next week i can try in a factory. Therefore I have to send first this packet: byte[] pacchetto = new byte[20]; int errore = 0; pacchetto[0] = 70; //header -> FINSpacchetto[1] = 73;pacchetto[2] = 78;pacchetto[3] = 83;pacchetto[4] = 0; //length = 12 bytespacchetto[5] = 0;pacchetto[6] = 0;pacchetto[7] = 12;pacchetto[8] = 0; //command = 0pacchetto[9] = 0;pacchetto[10] = 0;pacchetto[11] = 0;pacchetto[12] = 0; //error code = 0pacchetto[13] = 0;pacchetto[14] = 0;pacchetto[15] = 0;pacchetto[16] = 0; //client node address automatically obtained when it is set to 0pacchetto[17] = 0;pacchetto[18] = 0;pacchetto[19] = 0; Get response of PLC that return me the client node address. after this I can send this command: byte[] pacchetto = new byte[34]; pacchetto[0] = 70; //header -> FINSpacchetto[1] = 73;pacchetto[2] = 78;pacchetto[3] = 83;pacchetto[4] = 0; //length after commandpacchetto[5] = 0;pacchetto[6] = 0;pacchetto[7] = 22;pacchetto[8] = 0; //command = 2pacchetto[9] = 0;pacchetto[10] = 0;pacchetto[11] = 2;pacchetto[12] = 0; //error code = 0pacchetto[13] = 0;pacchetto[14] = 0;pacchetto[15] = 0;//fins framepacchetto[16] = -128; //icf pacchetto[17] = 0; //rsvpacchetto[18] = 2; //gctpacchetto[19] = 0; //dnapacchetto[20] = 0; //da1pacchetto[21] = 0; //da2 pacchetto[22] = 0; //snapacchetto[23] = clientNode; //sa1pacchetto[24] = 0; //sa2pacchetto[25] = 100; //sidpacchetto[26] = 1; //mrcpacchetto[27] = 1; //srcpacchetto[28] = -126; //tipo di memoria 82 -> DMpacchetto[29] = 0; //word iniziopacchetto[30] = -116; pacchetto[31] = 0; //bit iniziopacchetto[32] = 0;pacchetto[33] = 32; //quante word And then read the response that it will contain the value of word. Right? I have done a simple class that I have attached. Can you try and tell me if thre is any error? Thanks a lot Sparky the best user in a lot forum. import java.net.*;import java.io.*;public class JavaFins { //variabili connessione Socket client = null; String ip = ""; int port = 0; //varibili per leggere e scrivere OutputStream out_data = null; PrintStream printStream = null; InputStream inputStream; byte[] buffer = null; byte clientNode = 0, serverNode = 0; JavaFins() { System.out.println("Start program... \n"); ip = "localhost"; port = 9600; } private void Connetti() { try { client = new Socket(ip, port); out_data = client.getOutputStream(); inputStream = client.getInputStream(); System.out.println("Connected to " + client.getInetAddress() + " on port: " + client.getPort() + "\n" ); } catch (UnknownHostException e) { // TODO Auto-generated catch block e.printStackTrace(); } catch (IOException e) { // TODO Auto-generated catch block e.printStackTrace(); } } private void Leggi() { byte[] pacchetto = new byte[20]; int errore = 0; pacchetto[0] = 70; //header -> FINS pacchetto[1] = 73; pacchetto[2] = 78; pacchetto[3] = 83; pacchetto[4] = 0; //length = 12 bytes pacchetto[5] = 0; pacchetto[6] = 0; pacchetto[7] = 12; pacchetto[8] = 0; //command = 0 pacchetto[9] = 0; pacchetto[10] = 0; pacchetto[11] = 0; pacchetto[12] = 0; //error code = 0 pacchetto[13] = 0; pacchetto[14] = 0; pacchetto[15] = 0; pacchetto[16] = 0; //client node address automatically obtained when it is set to 0 pacchetto[17] = 0; pacchetto[18] = 0; pacchetto[19] = 0; try { printStream = new PrintStream(client.getOutputStream(), true); //apro stream di scrittura printStream.write(pacchetto); //mando pacchetto al PLC System.out.println("Attendo risposta..."); while(true) { //aggiungere thread.slepp per non interrompere il pacchetto ? if(inputStream.available()>0 && inputStream!=null ) { inputStream.read(buffer = new byte[inputStream.available()]); break; } } if( buffer.length > 0) //se l'array di byte ricevuto è maggiore di zero { errore = buffer[15]; if( errore == 0 ) //byte di eventuali errori { clientNode = buffer[20]; //byte clientNode serverNode = buffer[23]; //byte serverNode StampoPacchetto(buffer); //stampo pacchetto } else { if(errore == 1) { System.out.println("The header is not FINS..."); } else { if( errore == 2 ) { System.out.println("The data length is too long..."); } else { if( errore == 3) { System.out.println("Command is not supported...."); } else { if( errore == 20) { System.out.println("Alla connections are in use..."); } else { if( errore == 21) { System.out.println("The specific node is already connected..."); } else { if(errore == 22) { System.out.println("Attempt to access a protected node from an unspecific ip address..."); } else { if( errore == 23) { System.out.println("Fins node address is out of range..."); } else { if(errore == 24) { System.out.println("Fins node address is being used by the client and server...."); } else { if(errore == 25) { System.out.println("All node addresses avaiable for allocation have been used..."); } } } } } } } } } } } } catch (IOException e) { // TODO Auto-generated catch block e.printStackTrace(); } } private void LeggiWord() { byte[] pacchetto = new byte[34]; pacchetto[0] = 70; //header -> FINS pacchetto[1] = 73; pacchetto[2] = 78; pacchetto[3] = 83; pacchetto[4] = 0; //length after command pacchetto[5] = 0; pacchetto[6] = 0; pacchetto[7] = 22; pacchetto[8] = 0; //command = 2 pacchetto[9] = 0; pacchetto[10] = 0; pacchetto[11] = 2; pacchetto[12] = 0; //error code = 0 pacchetto[13] = 0; pacchetto[14] = 0; pacchetto[15] = 0; //fins frame pacchetto[16] = -128; //icf pacchetto[17] = 0; //rsv pacchetto[18] = 2; //gct pacchetto[19] = 0; //dna pacchetto[20] = 0; //da1 pacchetto[21] = 0; //da2 pacchetto[22] = 0; //sna pacchetto[23] = clientNode; //sa1 pacchetto[24] = 0; //sa2 pacchetto[25] = 100; //sid pacchetto[26] = 1; //mrc pacchetto[27] = 1; //src pacchetto[28] = -126; //tipo di memoria 82 -> DM pacchetto[29] = 0; //word inizio pacchetto[30] = -116; pacchetto[31] = 0; //bit inizio pacchetto[32] = 0; pacchetto[33] = 32; //quante word //invio pacchetto che legge 150 word dal plc try { printStream = new PrintStream(client.getOutputStream(), true); //apro stream di scrittura printStream.write(pacchetto); //mando pacchetto al PLC System.out.println("Attendo risposta..."); while(true) { //aggiungere thread.slepp per non interrompere il pacchetto ? if(inputStream.available()>0 && inputStream!=null ) { inputStream.read(buffer = new byte[inputStream.available()]); break; } } if( buffer.length > 0) //se l'array di byte ricevuto è maggiore di zero { if( buffer[15] == 0 ) //byte di eventuali errori { //buffer[28] - buffer[29] ricevo MRES e SRES //buffer[30] -> inizio dei dati StampoPacchetto(buffer); //stampo pacchetto } else System.out.println("Errore pacchetto..."); } } catch (IOException e) { // TODO Auto-generated catch block e.printStackTrace(); } } //FUNZIONE CHE MI STAMPA I BYTE DI UN PACCHETTO (ARRAY DI BYTE) public void StampoPacchetto(byte[] pacchettoDaServer) { for(byte b: pacchettoDaServer) { // print character System.out.print(b + " "); } System.out.println(" \n"); } public static void main(String args[]) { JavaFins prova = new JavaFins(); prova.Connetti(); //connetto al plc prova.Leggi(); //leggo client node address -> PAG 177 fotocopia prova.LeggiWord(); // leggo word allarmi System.out.println("Fine..."); } }Save the file like JavaFins.java after in your terminal you have to do: cd path where file is saved javac JavaFins.java java JavaFins Thanks...

Share this post


Link to post
Share on other sites
I made three changes: 1) ip = "192.168.0.10"; (changed from localhost to ip address) 2)In LeggiWord(): pacchetto[7] = 26; (changed from 22 to 26) 3) In Leggi(): pacchetto[19] = -56; (changed to my node 200 from 0) Then, your code worked fine! run:Start program... Connected to /192.168.0.10 on port: 9600 Attendo risposta...70 73 78 83 0 0 0 16 0 0 0 1 0 0 0 0 0 0 0 -56 0 0 0 10 Attendo risposta...70 73 78 83 0 0 0 86 0 0 0 2 0 0 0 0 -64 0 2 0 -56 0 0 10 0 100 1 1 0 0 0 0 0 0 0 0 0 0 0 5 0 0 0 0 0 0 0 0 0 0 0 0 51 50 1 80 48 48 92 92 0 0 0 4 0 -26 10 70 0 116 0 0 0 0 0 0 10 70 0 0 0 0 0 0 0 0 0 0 0 13 0 0 0 0 Fine...BUILD SUCCESSFUL (total time: 2 seconds)
1 person likes this

Share this post


Link to post
Share on other sites
Ok, I can not way to try the driver.... next week I tell you if it works in the factory... :) Thanks a lot.

Share this post


Link to post
Share on other sites

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!


Register a new account

Sign in

Already have an account? Sign in here.


Sign In Now
Sign in to follow this  
Followers 0