Posted 25 Nov 2020 Hi I am looking for a way to read and write data from PLC omron words, bits via FINS or EtherNet/IP protocol using python programming lang. Does anyone have any results in this? I really want to see your work, because all my attempts have failed. Thanks. Share this post Link to post Share on other sites
Posted 27 Nov 2020 Good day, i am testing this script and have a simle relesult: but I can’t read the memory of the plc bits and words. i am use this manual for experements: https://github.com/pjkundert/cpppo/files/1088579/EIP21.omron.pdf import sys import time from cpppo.server.enip.get_attribute import proxy_simple from cpppo.server.enip import poll from cpppo.server.enip.get_attribute import proxy_simple as device product_name, = proxy_simple ("192.168.135.60") .read ([('@ 1/1/7', 'SSTRING')]) var1 = product_name print(product_name) if var1 == ['CJ2M-EIP21']: print('connection comp.') data2, = proxy_simple ("192.168.135.60") .read ([('@ 196/0/100', 'INT')]) var2 = data2 if var2 == [4]: print('CPU in execution mode') if var2 == [2]: print('CPU in monitoring mode') if var2 == [1]: print('CPU in stop mode') Share this post Link to post Share on other sites
Posted 30 Nov 2020 These are always interesting and fun projects to play around with. By today's standards, you can get HMIs, SCADA and/or PC drivers to accomplish what you are trying to do. The costs will vary. You can communicate with Omron PLCs in a few different methods depending upon the PLC hardware. Almost any programming language will work. I've done a few in the old days using BASIC language and Omron's Host Link commands (RS232C). You are using Ethernet so you have found the options are FINS and Ethernet/IP. Ethernet/IP will prove to be very difficult. Unless you are well versed in EtherNet/IP protocol, it will consume your time in understanding it, deciding on the type of EIP method use, then establishing communications with the PLC. FINS will be your best bet if you wish to pursue your quest. There are several examples using DotNet and ActiveX in the downloads section here at MrPLC. https://forums.mrplc.com/index.php?/files/category/48-utilities/ It should be easy enough to see exactly what the programming is sending the PLC. You'll just need to change your code to Python. Along with the examples, you'll also want to use the FINS Command Reference Manual W227 to better understand what these programs are doing. Share this post Link to post Share on other sites
Posted 30 Nov 2020 A colleague of mine has done extensive work with Python and communicating with Omron PLCs. Here is some FINS Python stuff that might be useful: https://aphyt.com/index.php/projects Share this post Link to post Share on other sites
Posted 1 Dec 2020 16 hours ago, IO_Rack said: These are always interesting and fun projects to play around with. By today's standards, you can get HMIs, SCADA and/or PC drivers to accomplish what you are trying to do. The costs will vary. You can communicate with Omron PLCs in a few different methods depending upon the PLC hardware. Almost any programming language will work. I've done a few in the old days using BASIC language and Omron's Host Link commands (RS232C). You are using Ethernet so you have found the options are FINS and Ethernet/IP. Ethernet/IP will prove to be very difficult. Unless you are well versed in EtherNet/IP protocol, it will consume your time in understanding it, deciding on the type of EIP method use, then establishing communications with the PLC. FINS will be your best bet if you wish to pursue your quest. There are several examples using DotNet and ActiveX in the downloads section here at MrPLC. https://forums.mrplc.com/index.php?/files/category/48-utilities/ It should be easy enough to see exactly what the programming is sending the PLC. You'll just need to change your code to Python. Along with the examples, you'll also want to use the FINS Command Reference Manual W227 to better understand what these programs are doing. Thank you very mutch for your answer, i will try your suggestion. Share this post Link to post Share on other sites
Posted 1 Dec 2020 15 hours ago, Michael Walsh said: A colleague of mine has done extensive work with Python and communicating with Omron PLCs. Here is some FINS Python stuff that might be useful: https://aphyt.com/index.php/projects Thank you very mutch for your answer, i will try it, and writing result test. Share this post Link to post Share on other sites
Posted 1 Dec 2020 2 hours ago, TBLLC said: Thank you very mutch for your answer, i will try it, and writing result test. mem_area = fins_instance.memory_area_read(fins.FinsPLCMemoryAreas().CIO_WORD,b'\x00\x64\x00') CIO reading great worked, thank you very mutch, but how to read D memory? do you have example? Thanks. Where can I find a description of the library? Share this post Link to post Share on other sites
Posted 1 Dec 2020 (edited) good news im have a result read D (DM) area memory, use this request: mem_area_dm_word = fins_instance.memory_area_read(FinsPLCMemoryAreas().DATA_MEMORY_WORD,b'\x00\x03\x00') print(mem_area_dm_word) DATA_MEMORY_WORD,b'\x00\x03\x00') = D00003 but it's impossible read D > 100 D1234 for an example, how to create a request? for read D > 100 where to find the author of the library? Edited 1 Dec 2020 by TBLLC Share this post Link to post Share on other sites
Posted 1 Dec 2020 I received a reply from the author of the library (his email is also in the source code and on the contact page at the link provided above): It is all hex according to the memory address designation of FINS so 1234 would be \x04\xd2 and since it is a DM, the bit designation is \x00, so it would be: mem_area_dm_word = fins_instance.memory_area_read(FinsPLCMemoryAreas().DATA_MEMORY_WORD,b'\x04\xd2\x00') print(mem_area_dm_word) Share this post Link to post Share on other sites
Posted 2 Dec 2020 (edited) 13 hours ago, Michael Walsh said: I received a reply from the author of the library (his email is also in the source code and on the contact page at the link provided above): It is all hex according to the memory address designation of FINS so 1234 would be \x04\xd2 and since it is a DM, the bit designation is \x00, so it would be: Thank you very mutch for your fast feedback and and special thanks to the author for support, some more one question please: When i read dm data for example dm3 register (2 characters) i get correct result request: mem_area_dm_word = fins_instance.memory_area_read(FinsPLCMemoryAreas().DATA_MEMORY_WORD,b'\x00\x03\x00') answer: b'\xc0\x00\x02\x00\x19\x00\x00\x01\x00`\x01\x01\x00\x00\x00\x11' PLC memory table have result: 0011 if i read a value more than 2 characters: request: mem_area_dm_word = fins_instance.memory_area_read(FinsPLCMemoryAreas().DATA_MEMORY_WORD,b'\x00\x06\x00') answer: b'\xc0\x00\x02\x00\x19\x00\x00\x01\x00`\x01\x01\x00\x00%U' PLC memory table have result: 2557 Using this request format if answer data < 1000 result is correct accordingly if answer > 1000 result is incorrect calculated by checking different DM registers as a result there is such a dependence Edited 2 Dec 2020 by TBLLC Share this post Link to post Share on other sites
Posted 2 Dec 2020 From the author: The print statement is printing raw bytes as that is the response from the PLC. By default Python’s print will format any printable characters as ASCII, which you can detect by the fact that they are not preceded by the \x statement indicating they are hex. With this in mind the % character is ASCII value hex \x25 and U is ASCII value hex \x55, which leads me to believe it is a process value and the least significant byte is noise (hence the 55 vs 57 difference from the memory table). Normally the programmer would slice the bytes that they read off the response and format them the way that the intend to use them (FINS doesn’t know if that hex value is an integer, unsigned integer, real, etc.). If you always want the response in hex, you can use the binascii.hexlify library. Share this post Link to post Share on other sites
Posted 4 Dec 2020 On 02.12.2020 at 6:34 PM, Michael Walsh said: From the author: The print statement is printing raw bytes as that is the response from the PLC. By default Python’s print will format any printable characters as ASCII, which you can detect by the fact that they are not preceded by the \x statement indicating they are hex. With this in mind the % character is ASCII value hex \x25 and U is ASCII value hex \x55, which leads me to believe it is a process value and the least significant byte is noise (hence the 55 vs 57 difference from the memory table). Normally the programmer would slice the bytes that they read off the response and format them the way that the intend to use them (FINS doesn’t know if that hex value is an integer, unsigned integer, real, etc.). If you always want the response in hex, you can use the binascii.hexlify library. Thank you wery mutch for your answer this is very important for me. Share this post Link to post Share on other sites
Posted 22 Mar 2021 On 11/30/2020 at 10:41 PM, Michael Walsh said: A colleague of mine has done extensive work with Python and communicating with Omron PLCs. Here is some FINS Python stuff that might be useful: https://aphyt.com/index.php/projects Hi, do you happen to have an example for reading and writing Boolean IO via FINS? I tried using the examples that was in the link attached but ran into several errors: 1. My python compiler was not able to recognize "memory_area.write" 2. For "CIO_WORD", my compiler says Unresolved attribute reference 'CIO_WORD' for class 'FinsPLCMemoryAreas'. For this, based on my understanding it is because the example was made for words and bits, correct me if I'm wrong. I hope there is some solutions or examples to my errors and problems. Thanks in advance fins_instance.memory_area_write(fins.FinsPLCMemoryAreas().CIO_WORD,b'\x00\x64\x00',b'\x00\x1f',1) Share this post Link to post Share on other sites
Posted 30 Sep 2021 (edited) Hi there. I'm trying to communicate to a CJ1M-CPU11 PLC using this Python FINS library. I've copied the sample program but I don't write in CIO memory nor read it. Is there any other configuration beside IP addresses? I don't know if this parameters are default or I should change something else: fins_instance.dest_node_add=1 fins_instance.srce_node_add=25 Thanks a lot! Edit: Alright I solved it. Didn't know node number was last IP address digit until I researched a bit Edited 30 Sep 2021 by Robror Share this post Link to post Share on other sites
Posted 5 Oct 2021 I'm using a CJ2M CPU33. I used the same python library with success. Here is a sample of code i used to put results in excel. import time import fins.udp fins_instance = fins.udp.UDPFinsConnection() fins_instance.connect('192.168.0.14') fins_instance.dest_node_add=14 fins_instance.srce_node_add=249 for i in range(1): mem_area = fins_instance.memory_area_read(fins.FinsPLCMemoryAreas().DATA_MEMORY_WORD,b'\x00\x64\x00') time.sleep(1) mem_area = int.from_bytes(mem_area,'big') mem_area = bin(mem_area) print(mem_area) from openpyxl import load_workbook wb = load_workbook(filename = 'bin2hex.xlsm',keep_vba=True) ws1 = wb.active ws1['H1'] = mem_area wb.save('bin2hex.xlsm') Share this post Link to post Share on other sites
Posted 3 Nov 2021 Hi there! So i've been messing around with the library Michael shared in order to send/receive data from a CJ1M CPU. My only question regarding the use of this library is: is it possible to disconnect and connect again? I've been trying to, but whenever I try to connect again I get "[WinError 10022] An invalid argument was supplied" error. I tried calling __del__ method of UDPFinsConnection class with no result. I've been reading about sockets in Pyton, but my knowledge on the subject is very limited and I was wondering if someone knew something about this connections in Python. Thanks in advance! Share this post Link to post Share on other sites
Posted 11 Feb 2022 I have not experienced that issue using that module. If you disconnect the cable and plug back in it will that a second for the pc to reestablish the lan connection. Share this post Link to post Share on other sites