JoelBender / bacpypes

BACpypes provides a BACnet application layer and network layer written in Python for daemons, scripting, and graphical interfaces.
MIT License
296 stars 128 forks source link

How to use bacpypes with BACnet ethernet #98

Open hoangdungt2 opened 7 years ago

hoangdungt2 commented 7 years ago

Hi,

I'm new to python and bacpypes, I tried to look at the example but seems to me all are for BACnet/IP. I wonder if any of you can help to write a BACnet/Ethernet example, I would be very grateful.

Thank you very much

JoelBender commented 7 years ago

There are two ways that I have found for doing this work, raw sockets on Linux and winpcap on Windows (I prowled around the source code for the current version of VTS to see how I had accomplished this before and I can't find it yet). If you would like to try a raw sockets implementation I could include in the project that would be awesome!

Start by forking the project, duplicate the udp.py module as eth.py, rename UDP to Ethernet (like UDPActor to EthernetActor), change the socket type request in the director:

        # ask the dispatcher for a socket
        self.create_socket(socket.AF_PACKET, socket.SOCK_RAW)

Add to the handle_read() function after receiving the packet to split out the destination address, source address, length, and DSAP and SSAP fields. Check to make sure that DSAP and SSAP are 0x82 for BACnet. The rest of the content goes into the pduData field for a PDU going up the stack.

Add to the handle_write() function after getting the request to build an Ethernet frame with the same header fields (make sure you get the length right) and the rest of the packet is the pduData attribute.

In the BVLL service layer there is code for recognizing Annex-H vs Annex-J UDP packets, which you won't need, but there is code for recognizing when the source and destination addresses are local broadcast, so you'll need to translate those as well.

I'll leave this issue open for your comments and for me to add this in the future, otherwise you can close it and let me know what your fork is called.

JoelBender commented 7 years ago

The BACnet Firewall Router project has an implementation in BFREthernet.cpp that should be very close to what is needed. I knew I had that code someplace :-)

hoangdungt2 commented 7 years ago

Hi JoelBender,

Thank you very much for the help. To be honest, I'm not very familiar with BACnet raw data management. Actually, I was hoping bacpypes can allow me to just specify the ethernet adapter then I can just do whois then read/write property directly to the discovered devices. I see this https://sourceforge.net/projects/yetanotherbacnetexplorer/ allow me to but it is in C# so I was hoping to have something similar but in Python. Thanks a lot.

JoelBender commented 7 years ago

From BacnetTransportEthernet.cs it is stacked on top of SharpPcap which is in turn stacked on WinPcap, and there is a winpcapy project that is very similar, so there is definitely a way forward.