private void SendData(S7OexchangeBlock data) { if (!Disposed) { int len = Marshal.SizeOf(data); byte[] buffer = new byte[len]; data.headerlength = 80; //Length of the Header (always 80) (but the 4 first unkown bytes are not count) data.rb_type = 2; //rb_type is always 2 data.offset_1 = 80; //Offset of the Begin of userdata (but the 4 first unkown bytes are not count) IntPtr ptr = Marshal.AllocHGlobal(len); Marshal.StructureToPtr(data, ptr, true); Marshal.Copy(ptr, buffer, 0, len); Marshal.FreeHGlobal(ptr); int ret = SCP_send(_connectionHandle, (ushort)(data.seg_length_1 + data.headerlength), buffer); if (ret < 0) { throw new S7OnlineException(SCP_get_errno()); } } else { throw new ObjectDisposedException(this.ToString()); } }
private void DisconnectPlcsimStatemachine() { switch (m_PlcsimConnectionState) { case PlcsimConnectionState.DisconnectState1: S7OexchangeBlock fdr = new S7OexchangeBlock(); fdr = GetNewS7OexchangeBlock(user: 0, rb_type: 2, subsystem: 0x40, opcode: 12, response: 0xffff); fdr.fill_length_1 = 0; fdr.seg_length_1 = 0; fdr.offset_1 = 80; fdr.application_block_opcode = m_application_block_opcode; fdr.application_block_subsystem = m_application_block_subsystem; SendS7OExchangeBlockToPlcsim(fdr); // Simatic applications use a two-step disconnect, but this sometimes makes problems. // So don't use it anymore, works also without this. // //m_PlcsimConnectionState = PlcsimConnectionState.DisconnectState2; //break; //case PlcsimConnectionState.DisconnectState2: //rec = ReceiveFromPlcsimDirect(); //if (rec.opcode == 0x0c && rec.response == 0x0001) //{ // m_PlcsimConnectionState = PlcsimConnectionState.NotConnected; // ExitThisThread(); //} m_PlcsimConnectionState = PlcsimConnectionState.NotConnected; ExitThisThread(); break; } }
public S7OnlineInterface(string EntryPoint) { _entryPoint = EntryPoint; _connectionHandle = SCP_open(_entryPoint); if (_connectionHandle < 0) { this.Dispose(); throw new S7OnlineException(SCP_get_errno()); } S7OexchangeBlock fdr = new S7OexchangeBlock(); formBackgroundThread = new Thread(new ThreadStart(createFormInOtherThread)); formBackgroundThread.IsBackground = true; formBackgroundThread.Start(); //_myForm = new _intForm(_connectionHandle, Marshal.SizeOf(fdr), this); //SetSinecHWndMsg(_connectionHandle, _myForm.Handle, WM_SINEC); while (!WndProcReady) { } }
public void DisconnectPlc(Connection conn) { conn.ConnectionEstablished = false; S7OexchangeBlock fdr; if (conn.ConnectionConfig.ConnectionToEthernet) { fdr = new S7OexchangeBlock(); fdr.user = (ushort)conn.ConnectionNumber; fdr.subsystem = 64; fdr.opcode = 8; fdr.response = 255; fdr.application_block_opcode = conn.application_block_opcode; SendData(fdr); RecieveData((ushort)conn.ConnectionNumber); } fdr = new S7OexchangeBlock(); fdr.user = (ushort)conn.ConnectionNumber; fdr.subsystem = 64; fdr.opcode = 0xC; fdr.response = 255; fdr.application_block_service = 0x8000; fdr.application_block_opcode = conn.application_block_opcode; fdr.application_block_subsystem = conn.application_block_subsystem; SendData(fdr); RecieveData((ushort)conn.ConnectionNumber); ConnectionsList.Remove(conn.ConnectionNumber); }
protected override void WndProc(ref Message m) { if (m.Msg == WM_SINEC) //WM_SINEC Message recieved, recieve Data { int[] rec_len = new int[1]; byte[] buffer = new byte[fdrlen]; SCP_receive(_connectionHandle, 0, rec_len, (ushort)fdrlen, buffer); GCHandle handle = GCHandle.Alloc(buffer, GCHandleType.Pinned); S7OexchangeBlock rec = (S7OexchangeBlock)Marshal.PtrToStructure(handle.AddrOfPinnedObject(), typeof(S7OexchangeBlock)); handle.Free(); if (Interface.ConnectionsList[rec.user].ConnectionEstablished) { Interface.ConnectionsList[rec.user].SetRecievedPdu(new Pdu(rec.user_data_1)); } else { Interface.ConnectionsList[rec.user].RecievedData = rec; } } else { base.WndProc(ref m); } }
protected void DumpS7OexchangeBlock(S7OexchangeBlock fd) { string dump; dump = ("******************** S7OexchangeBlock **********************************" + Environment.NewLine); dump += ("** Header Start **" + Environment.NewLine); //dump += ("unknown : 0x" + String.Format("{0:X02}", fd.unknown[0] + fd.unknown[1] + Environment.NewLine); dump += ("headerlength : " + fd.headerlength + Environment.NewLine); dump += ("user : 0x" + String.Format("{0:X02}", fd.user) + Environment.NewLine); dump += ("rb_type : 0x" + String.Format("{0:X02}", fd.rb_type) + Environment.NewLine); dump += ("priority : 0x" + String.Format("{0:X02}", fd.priority) + Environment.NewLine); dump += ("reserved_1 : 0x" + String.Format("{0:X02}", fd.reserved_1) + Environment.NewLine); dump += ("reserved_2 : 0x" + String.Format("{0:X02}", fd.reserved_2) + Environment.NewLine); dump += ("subsystem : 0x" + String.Format("{0:X02}", fd.subsystem) + Environment.NewLine); dump += ("opcode : 0x" + String.Format("{0:X02}", fd.opcode) + Environment.NewLine); dump += ("response : 0x" + String.Format("{0:X02}", fd.response) + Environment.NewLine); dump += ("fill_length_1: 0x" + String.Format("{0:X02}", fd.fill_length_1) + Environment.NewLine); dump += ("reserved_3 : 0x" + String.Format("{0:X02}", fd.reserved_3) + Environment.NewLine); dump += ("seg_length_1 : 0x" + String.Format("{0:X02}", fd.seg_length_1) + Environment.NewLine); dump += ("offset_1 : 0x" + String.Format("{0:X02}", fd.offset_1) + Environment.NewLine); dump += ("reserved_4 : 0x" + String.Format("{0:X02}", fd.reserved_4) + Environment.NewLine); dump += ("fill_length_2: 0x" + String.Format("{0:X02}", fd.fill_length_2) + Environment.NewLine); dump += ("reserved_5 : 0x" + String.Format("{0:X02}", fd.reserved_5) + Environment.NewLine); dump += ("seg_length_2 : 0x" + String.Format("{0:X02}", fd.seg_length_2) + Environment.NewLine); dump += ("offset_2 : 0x" + String.Format("{0:X02}", fd.offset_2) + Environment.NewLine); dump += ("reserved_6 : 0x" + String.Format("{0:X02}", fd.reserved_6) + Environment.NewLine); dump += ("** End of Header **" + Environment.NewLine); dump += ("** Start of application Block **" + Environment.NewLine); dump += ("application_block_opcode : 0x" + String.Format("{0:X02}", fd.application_block_opcode) + Environment.NewLine); dump += ("application_block_subsystem : 0x" + String.Format("{0:X02}", fd.application_block_subsystem) + Environment.NewLine); dump += ("application_block_id : 0x" + String.Format("{0:X02}", fd.application_block_id) + Environment.NewLine); dump += ("application_block_service : 0x" + String.Format("{0:X02}", fd.application_block_service) + Environment.NewLine); dump += ("application_block_local_address_station : 0x" + String.Format("{0:X02}", fd.application_block_local_address_station) + Environment.NewLine); dump += ("application_block_local_address_segment : 0x" + String.Format("{0:X02}", fd.application_block_local_address_segment) + Environment.NewLine); dump += ("application_block_ssap : 0x" + String.Format("{0:X02}", fd.application_block_ssap) + Environment.NewLine); dump += ("application_block_dsap : 0x" + String.Format("{0:X02}", fd.application_block_dsap) + Environment.NewLine); dump += ("application_block_remote_address_station : 0x" + String.Format("{0:X02}", fd.application_block_remote_address_station) + Environment.NewLine); dump += ("application_block_remote_address_segment : 0x" + String.Format("{0:X02}", fd.application_block_remote_address_segment) + Environment.NewLine); dump += ("application_block_service_class : 0x" + String.Format("{0:X02}", fd.application_block_service_class) + Environment.NewLine); dump += ("application_block_receive_l_sdu_length : 0x" + String.Format("{0:X02}", fd.application_block_receive_l_sdu_length) + Environment.NewLine); dump += ("application_block_reserved_1 : 0x" + String.Format("{0:X02}", fd.application_block_reserved_1) + Environment.NewLine); dump += ("application_block_reserved : 0x" + String.Format("{0:X02}", fd.application_block_reserved) + Environment.NewLine); dump += ("application_block_send_l_sdu_length : 0x" + String.Format("{0:X02}", fd.application_block_send_l_sdu_length) + Environment.NewLine); dump += ("application_block_l_status : 0x" + String.Format("{0:X02}", fd.application_block_l_status) + Environment.NewLine); dump += ("** End of application Block **" + Environment.NewLine); dump += ("** Start user_data_1 **" + Environment.NewLine); if (fd.user_data_1 != null) { dump += HexDumping.Utils.HexDump(fd.user_data_1, fd.user_data_1.Length); } dump += ("** End user_data_1 **" + Environment.NewLine); dump += ("**************************************************************"); DoTrace(dump, false); }
private S7OexchangeBlock RecieveData(ushort myConnNr) { while (ConnectionsList[myConnNr].RecievedData == null) { } S7OexchangeBlock rec = (S7OexchangeBlock)ConnectionsList[myConnNr].RecievedData; ConnectionsList[myConnNr].RecievedData = null; return(rec); }
protected S7OexchangeBlock GetNewS7OexchangeBlock(ushort user, byte rb_type, byte subsystem, byte opcode, ushort response) { S7OexchangeBlock block = new S7OexchangeBlock(); block.headerlength = 80; block.user = user; block.rb_type = rb_type; block.subsystem = subsystem; block.opcode = opcode; block.response = response; return(block); }
private void createFormInOtherThread() { try { S7OexchangeBlock fdr = new S7OexchangeBlock(); _myForm = new _intForm(_connectionHandle, Marshal.SizeOf(fdr), this); SetSinecHWndMsg(_connectionHandle, _myForm.Handle, WM_SINEC); WndProcReady = true; Application.Run(); } catch (ThreadAbortException) { } }
private void ReceiveFromPlcsimAndSendBack() { int[] rec_len = new int[1]; byte[] buffer = new byte[m_FdrLen]; if (SCP_receive(m_connectionHandle, 0, rec_len, (ushort)m_FdrLen, buffer) == -1) { if (m_connectionHandle > 0) { if (m_PlcsimConnectionState == PlcsimConnectionState.ConnectState1 || m_PlcsimConnectionState == PlcsimConnectionState.ConnectState2 || m_PlcsimConnectionState == PlcsimConnectionState.ConnectState3) { SendConnectErrorMessage("ERROR: Connect failed in SCP_receive at " + m_PlcsimConnectionState.ToString()); } else { int errno = SCP_get_errno(); string errtxt = GetErrTxt(errno); SendErrorMessage("ERROR: SCP_receive() failed. m_connectionHandle = " + m_connectionHandle + " SCP_get_errno=" + errno + " (" + errtxt + ")"); } } ExitThisThread(); return; } GCHandle handle = GCHandle.Alloc(buffer, GCHandleType.Pinned); S7OexchangeBlock rec = (S7OexchangeBlock)Marshal.PtrToStructure(handle.AddrOfPinnedObject(), typeof(S7OexchangeBlock)); handle.Free(); if (rec.opcode == 6 && rec.response == 1) { // don't care } else if (rec.opcode == 7 && rec.response == 3) { byte[] recbytes = new byte[rec.fill_length_1]; Array.Copy(rec.user_data_1, recbytes, rec.fill_length_1); SendPduMessage(recbytes); S7OexchangeBlock snd = GetNewS7OexchangeBlock(user: 0, rb_type: 2, subsystem: 0x40, opcode: 7, response: 0xffff); snd.offset_1 = 80; snd.fill_length_1 = 0; snd.seg_length_1 = SEG_LENGTH_1; snd.application_block_opcode = rec.application_block_opcode; snd.application_block_subsystem = rec.application_block_subsystem; SendS7OExchangeBlockToPlcsim(snd); } }
protected S7OexchangeBlock ReceiveFromPlcsimDirect() { S7OexchangeBlock rec = new S7OexchangeBlock(); int[] rec_len = new int[1]; int len = Marshal.SizeOf(rec); byte[] buffer = new byte[len]; if (SCP_receive(m_connectionHandle, 0, rec_len, (ushort)len, buffer) == 0) { GCHandle handle = GCHandle.Alloc(buffer, GCHandleType.Pinned); rec = (S7OexchangeBlock)Marshal.PtrToStructure(handle.AddrOfPinnedObject(), typeof(S7OexchangeBlock)); handle.Free(); } return(rec); }
public void SendPdu(Pdu pdu, Connection connection) { if (!Disposed) { byte[] pdubytes = pdu.ToBytes(); S7OexchangeBlock fdr = new S7OexchangeBlock(); fdr.user = (ushort)connection.ConnectionNumber; fdr.subsystem = 64; fdr.opcode = 6; fdr.response = 255; fdr.fill_length_1 = (byte)pdubytes.Length; fdr.seg_length_1 = (byte)pdubytes.Length; fdr.application_block_opcode = connection.application_block_opcode; //if (!connection.ConnectionConfig.ConnectionToEthernet) fdr.application_block_subsystem = connection.application_block_subsystem; fdr.headerlength = 80; //Length of the Header (always 80) (but the 4 first unkown bytes are not count) fdr.rb_type = 2; //rb_type is always 2 fdr.offset_1 = 80; //Offset of the Begin of userdata (but the 4 first unkown bytes are not count) fdr.user_data_1 = new byte[260]; Array.Copy(pdubytes, fdr.user_data_1, pdubytes.Length); int len = Marshal.SizeOf(fdr); byte[] buffer = new byte[len]; IntPtr ptr = Marshal.AllocHGlobal(len); Marshal.StructureToPtr(fdr, ptr, true); Marshal.Copy(ptr, buffer, 0, len); Marshal.FreeHGlobal(ptr); int ret = SCP_send(_connectionHandle, (ushort)(fdr.seg_length_1 + fdr.headerlength), buffer); if (ret < 0) { throw new S7OnlineException(SCP_get_errno()); } } else { throw new ObjectDisposedException(this.ToString()); } }
public PlcS7onlineMsgPump(IPAddress plc_ipaddress, int rack, int slot) { m_PlcIPAddress = plc_ipaddress; m_PlcRack = rack; m_PlcSlot = slot; m_connectionHandle = -1; m_user = 1; m_PlcsimConnectionState = PlcsimConnectionState.NotConnected; S7OexchangeBlock fdr = new S7OexchangeBlock(); m_FdrLen = Marshal.SizeOf(fdr); m_TraceEnabled = false; if (m_TraceEnabled) { Trace.Listeners.Add(new TextWriterTraceListener("PlcsimS7online.log")); DoTrace("Start trace..."); } }
private void SendDataToPlcsim(WndProcMessage msg) { if (++m_user >= 32000) { m_user = 1; } S7OexchangeBlock snd = GetNewS7OexchangeBlock(user: m_user, rb_type: 2, subsystem: 0x40, opcode: 6, response: 0xff); snd.offset_1 = 80; snd.application_block_opcode = m_application_block_opcode; snd.application_block_subsystem = m_application_block_subsystem; snd.fill_length_1 = (ushort)msg.pdu.Length; snd.seg_length_1 = (ushort)msg.pdu.Length; snd.user_data_1 = new byte[SIZE_OF_USER_DATA_1]; Array.Copy(msg.pdu, snd.user_data_1, msg.pdu.Length); SendS7OExchangeBlockToPlcsim(snd); }
private void GetResponsePdu(Connection connection) { if (!Disposed) { S7OexchangeBlock fdr = new S7OexchangeBlock(); fdr.user = (ushort)connection.ConnectionNumber; fdr.subsystem = 64; fdr.opcode = 7; fdr.seg_length_1 = 480; fdr.response = 16642; fdr.application_block_opcode = connection.application_block_opcode; fdr.application_block_subsystem = connection.application_block_subsystem; fdr.headerlength = 80; //Length of the Header (always 80) (but the 4 first unkown bytes are not count) fdr.rb_type = 2; //rb_type is always 2 fdr.offset_1 = 80; //Offset of the Begin of userdata (but the 4 first unkown bytes are not count) fdr.user_data_1 = new byte[260]; int len = Marshal.SizeOf(fdr); byte[] buffer = new byte[len]; IntPtr ptr = Marshal.AllocHGlobal(len); Marshal.StructureToPtr(fdr, ptr, true); Marshal.Copy(ptr, buffer, 0, len); Marshal.FreeHGlobal(ptr); int ret = SCP_send(_connectionHandle, (ushort)(fdr.seg_length_1 + fdr.headerlength), buffer); if (ret < 0) { throw new S7OnlineException(SCP_get_errno()); } } else { throw new ObjectDisposedException(this.ToString()); } }
protected void SendS7OExchangeBlockToPlcsim(S7OexchangeBlock data) { int len = Marshal.SizeOf(data); byte[] buffer = new byte[len]; ushort send_len = (ushort)(data.seg_length_1 + data.headerlength); IntPtr ptr = Marshal.AllocHGlobal(len); Marshal.StructureToPtr(data, ptr, false); Marshal.Copy(ptr, buffer, 0, len); Marshal.DestroyStructure(ptr, typeof(S7OexchangeBlock)); Marshal.FreeHGlobal(ptr); int ret = SCP_send(m_connectionHandle, send_len, buffer); if (ret < 0) { SendErrorMessage("ERROR: SCP_send failed"); ExitThisThread(); } }
private void SendData(S7OexchangeBlock data) { if (!Disposed) { int len = Marshal.SizeOf(data); byte[] buffer = new byte[len]; data.headerlength = 80; //Length of the Header (always 80) (but the 4 first unkown bytes are not count) data.rb_type = 2; //rb_type is always 2 data.offset_1 = 80; //Offset of the Begin of userdata (but the 4 first unkown bytes are not count) IntPtr ptr = Marshal.AllocHGlobal(len); Marshal.StructureToPtr(data, ptr, true); Marshal.Copy(ptr, buffer, 0, len); Marshal.FreeHGlobal(ptr); int ret = SCP_send(_connectionHandle, (ushort) (data.seg_length_1 + data.headerlength), buffer); if (ret < 0) throw new S7OnlineException(SCP_get_errno()); } else { throw new ObjectDisposedException(this.ToString()); } }
private void GetResponsePdu(Connection connection) { if (!Disposed) { S7OexchangeBlock fdr = new S7OexchangeBlock(); fdr.user = (ushort)connection.ConnectionNumber; fdr.subsystem = 64; fdr.opcode = 7; fdr.seg_length_1 = 480; fdr.response = 16642; fdr.application_block_opcode = connection.application_block_opcode; fdr.application_block_subsystem = connection.application_block_subsystem; fdr.headerlength = 80; //Length of the Header (always 80) (but the 4 first unkown bytes are not count) fdr.rb_type = 2; //rb_type is always 2 fdr.offset_1 = 80; //Offset of the Begin of userdata (but the 4 first unkown bytes are not count) fdr.user_data_1 = new byte[260]; int len = Marshal.SizeOf(fdr); byte[] buffer = new byte[len]; IntPtr ptr = Marshal.AllocHGlobal(len); Marshal.StructureToPtr(fdr, ptr, true); Marshal.Copy(ptr, buffer, 0, len); Marshal.FreeHGlobal(ptr); int ret = SCP_send(_connectionHandle, (ushort)(fdr.seg_length_1 + fdr.headerlength), buffer); if (ret < 0) throw new S7OnlineException(SCP_get_errno()); } else { throw new ObjectDisposedException(this.ToString()); } }
public void SendPdu(Pdu pdu, Connection connection) { if (!Disposed) { byte[] pdubytes = pdu.ToBytes(); S7OexchangeBlock fdr = new S7OexchangeBlock(); fdr.user = (ushort) connection.ConnectionNumber; fdr.subsystem = 64; fdr.opcode = 6; fdr.response = 255; fdr.fill_length_1 = (byte) pdubytes.Length; fdr.seg_length_1 = (byte) pdubytes.Length; fdr.application_block_opcode = connection.application_block_opcode; //if (!connection.ConnectionConfig.ConnectionToEthernet) fdr.application_block_subsystem = connection.application_block_subsystem; fdr.headerlength = 80; //Length of the Header (always 80) (but the 4 first unkown bytes are not count) fdr.rb_type = 2; //rb_type is always 2 fdr.offset_1 = 80; //Offset of the Begin of userdata (but the 4 first unkown bytes are not count) fdr.user_data_1 = new byte[260]; Array.Copy(pdubytes, fdr.user_data_1, pdubytes.Length); int len = Marshal.SizeOf(fdr); byte[] buffer = new byte[len]; IntPtr ptr = Marshal.AllocHGlobal(len); Marshal.StructureToPtr(fdr, ptr, true); Marshal.Copy(ptr, buffer, 0, len); Marshal.FreeHGlobal(ptr); int ret = SCP_send(_connectionHandle, (ushort)(fdr.seg_length_1 + fdr.headerlength), buffer); if (ret < 0) throw new S7OnlineException(SCP_get_errno()); } else { throw new ObjectDisposedException(this.ToString()); } }
public void DisconnectPlc(Connection conn) { conn.ConnectionEstablished = false; S7OexchangeBlock fdr; if (conn.ConnectionConfig.ConnectionToEthernet) { fdr = new S7OexchangeBlock(); fdr.user = (ushort) conn.ConnectionNumber; fdr.subsystem = 64; fdr.opcode = 8; fdr.response = 255; fdr.application_block_opcode = conn.application_block_opcode; SendData(fdr); RecieveData((ushort) conn.ConnectionNumber); } fdr = new S7OexchangeBlock(); fdr.user = (ushort)conn.ConnectionNumber; fdr.subsystem = 64; fdr.opcode = 0xC; fdr.response = 255; fdr.application_block_service = 0x8000; fdr.application_block_opcode = conn.application_block_opcode; fdr.application_block_subsystem = conn.application_block_subsystem; SendData(fdr); RecieveData((ushort)conn.ConnectionNumber); ConnectionsList.Remove(conn.ConnectionNumber); }
public Connection ConnectPlc(ConnectionConfig config) { //eine eindeutige connection id erzeugen //in der connection eine liste der pdus pflegen, auf welche noch gewartet wird. //für die pdu welche asynchron kommt nummer 0 verwenden! S7OexchangeBlock fdr = new S7OexchangeBlock(); S7OexchangeBlock rec = new S7OexchangeBlock(); int len = Marshal.SizeOf(fdr); byte[] buffer = new byte[len]; IntPtr ptr; GCHandle handle; Connection retVal; while (ConnectionsList.ContainsKey(connNr)) { connNr++; if (connNr >= ushort.MaxValue) connNr = 1; } retVal = new Connection(this, config, 0); retVal.ConnectionNumber = connNr; ConnectionsList.Add(connNr, retVal); //Todo: //Im Feld fdr.user für jede Connection einen eigenen Wert verwenden, so das bei empfangen Daten auch //Festgestellt werden kann für welche Connection die sind. //Dann muss eine Liste geführt werden, in der die IDs und die zugehörige Connection gespeichert ist. //Wenn dann auf der ID was empfangen wird, wird das an die Connection weitergeleitet! if (!config.ConnectionToEthernet) { #region Telegramm 1 fdr.subsystem = 0x22; fdr.response = 0xFF; fdr.user = connNr;//0xFF; fdr.seg_length_1 = 0x80; fdr.priority = 1; fdr.application_block_service = (ushort)service_code.fdl_life_list_create_remote; SendData(fdr); rec = RecieveData(connNr); #endregion #region Telegramm 2 fdr.seg_length_1 = 0xF2; fdr.application_block_service = (ushort) service_code.fdl_read_value; SendData(fdr); rec = RecieveData(connNr); #endregion } #region Telegramm 3 (Ethernet 1) fdr = new S7OexchangeBlock(); fdr.user = connNr; fdr.response = 255; fdr.subsystem = 0x40; SendData(fdr); rec = RecieveData(connNr); retVal.application_block_opcode = rec.application_block_opcode; retVal.application_block_subsystem = rec.application_block_subsystem; #endregion #region Telegramm 4 (Ethernet 2) fdr = new S7OexchangeBlock(); fdr.user = connNr;// 111; fdr.subsystem = 64; fdr.opcode = 1; fdr.response = 255; fdr.fill_length_1 = 126; fdr.seg_length_1 = 126; fdr.application_block_opcode = retVal.application_block_opcode; fdr.application_block_ssap = 2; fdr.application_block_remote_address_station = 114; fdr.application_block_subsystem = retVal.application_block_subsystem; //When this is One it is a MPI Connection, zero means TCP Connection! UserDataConnectionConfig ud_cfg = new UserDataConnectionConfig(true); ud_cfg.rack_slot = (byte) (config.Slot + config.Rack*32); ud_cfg.connection_type = (byte) config.ConnectionType; if (config.ConnectionToEthernet) { ud_cfg.destination_1 = config.IPAddress.GetAddressBytes()[0]; ud_cfg.destination_2 = config.IPAddress.GetAddressBytes()[1]; ud_cfg.destination_3 = config.IPAddress.GetAddressBytes()[2]; ud_cfg.destination_4 = config.IPAddress.GetAddressBytes()[3]; } else ud_cfg.destination_1 = (byte) config.MPIAddress; if (config.Routing) { ud_cfg.routing_enabled = 0x01; ud_cfg.rack_slot = (byte) (config.RoutingSlot + config.RoutingRack*32); ud_cfg.size_of_subnet = 0x06; ud_cfg.routing_destination_1 = (byte) ((config.RoutingSubnet1 >> 8) & 0xFF); ud_cfg.routing_destination_2 = (byte) ((config.RoutingSubnet1) & 0xFF); ud_cfg.routing_destination_3 = (byte) ((config.RoutingSubnet2 >> 8) & 0xFF); ud_cfg.routing_destination_4 = (byte) ((config.RoutingSubnet2) & 0xFF); if (!config.RoutingToEthernet) { ud_cfg.size_of_routing_destination = 0x01; ud_cfg.routing_destination_1 = (byte) config.RoutingMPIAddres; ud_cfg.size_to_end = 0x09; } else { ud_cfg.size_of_routing_destination = 0x04; ud_cfg.routing_destination_1 = config.RoutingIPAddress.GetAddressBytes()[0]; ud_cfg.routing_destination_2 = config.RoutingIPAddress.GetAddressBytes()[1]; ud_cfg.routing_destination_3 = config.RoutingIPAddress.GetAddressBytes()[2]; ud_cfg.routing_destination_4 = config.RoutingIPAddress.GetAddressBytes()[3]; ud_cfg.size_to_end = 0x0C; } } ptr = Marshal.AllocHGlobal(Marshal.SizeOf(ud_cfg)); Marshal.StructureToPtr(ud_cfg, ptr, true); fdr.user_data_1 = new byte[260]; Marshal.Copy(ptr, fdr.user_data_1, 0, Marshal.SizeOf(ud_cfg)); Marshal.FreeHGlobal(ptr); SendData(fdr); rec = RecieveData(connNr); if (rec.response != 0x01) throw new S7OnlineException("S7Online: Error Connection to PLC"); #endregion #region Telegramm 5 (Ethernet 3) (this Telegramm sends a PDU) //5th Telegramm / TCP(3rd) Pdu pdu = new Pdu(1); pdu.Param.AddRange(new byte[] {0xF0, 0, 0, 1, 0, 1, 3, 0xc0}); SendPdu(pdu, retVal); Pdu recPdu = RecievePdu(connNr); #endregion #region Telegramm 6 (Ethernet 4) (get PDU size) fdr = new S7OexchangeBlock(); fdr.user = connNr;//0; fdr.subsystem = 64; fdr.opcode = 7; fdr.response = 16642; fdr.seg_length_1 = 480; fdr.application_block_opcode = retVal.application_block_opcode; fdr.application_block_subsystem = retVal.application_block_subsystem; SendData(fdr); recPdu = RecievePdu(connNr); retVal.PduSize = ByteFunctions.getU16from(recPdu.Param.ToArray(), 6); #endregion retVal.ConnectionEstablished = true; return retVal; }
public Connection ConnectPlc(ConnectionConfig config) { //eine eindeutige connection id erzeugen //in der connection eine liste der pdus pflegen, auf welche noch gewartet wird. //für die pdu welche asynchron kommt nummer 0 verwenden! S7OexchangeBlock fdr = new S7OexchangeBlock(); S7OexchangeBlock rec = new S7OexchangeBlock(); int len = Marshal.SizeOf(fdr); byte[] buffer = new byte[len]; IntPtr ptr; GCHandle handle; Connection retVal; while (ConnectionsList.ContainsKey(connNr)) { connNr++; if (connNr >= ushort.MaxValue) { connNr = 1; } } retVal = new Connection(this, config, 0); retVal.ConnectionNumber = connNr; ConnectionsList.Add(connNr, retVal); //Todo: //Im Feld fdr.user für jede Connection einen eigenen Wert verwenden, so das bei empfangen Daten auch //Festgestellt werden kann für welche Connection die sind. //Dann muss eine Liste geführt werden, in der die IDs und die zugehörige Connection gespeichert ist. //Wenn dann auf der ID was empfangen wird, wird das an die Connection weitergeleitet! if (!config.ConnectionToEthernet) { #region Telegramm 1 fdr.subsystem = 0x22; fdr.response = 0xFF; fdr.user = connNr;//0xFF; fdr.seg_length_1 = 0x80; fdr.priority = 1; fdr.application_block_service = (ushort)service_code.fdl_life_list_create_remote; SendData(fdr); rec = RecieveData(connNr); #endregion #region Telegramm 2 fdr.seg_length_1 = 0xF2; fdr.application_block_service = (ushort)service_code.fdl_read_value; SendData(fdr); rec = RecieveData(connNr); #endregion } #region Telegramm 3 (Ethernet 1) fdr = new S7OexchangeBlock(); fdr.user = connNr; fdr.response = 255; fdr.subsystem = 0x40; SendData(fdr); rec = RecieveData(connNr); retVal.application_block_opcode = rec.application_block_opcode; retVal.application_block_subsystem = rec.application_block_subsystem; #endregion #region Telegramm 4 (Ethernet 2) fdr = new S7OexchangeBlock(); fdr.user = connNr;// 111; fdr.subsystem = 64; fdr.opcode = 1; fdr.response = 255; fdr.fill_length_1 = 126; fdr.seg_length_1 = 126; fdr.application_block_opcode = retVal.application_block_opcode; fdr.application_block_ssap = 2; fdr.application_block_remote_address_station = 114; fdr.application_block_subsystem = retVal.application_block_subsystem; //When this is One it is a MPI Connection, zero means TCP Connection! UserDataConnectionConfig ud_cfg = new UserDataConnectionConfig(true); ud_cfg.rack_slot = (byte)(config.Slot + config.Rack * 32); ud_cfg.connection_type = (byte)config.ConnectionType; if (config.ConnectionToEthernet) { ud_cfg.destination_1 = config.IPAddress.GetAddressBytes()[0]; ud_cfg.destination_2 = config.IPAddress.GetAddressBytes()[1]; ud_cfg.destination_3 = config.IPAddress.GetAddressBytes()[2]; ud_cfg.destination_4 = config.IPAddress.GetAddressBytes()[3]; } else { ud_cfg.destination_1 = (byte)config.MPIAddress; } if (config.Routing) { ud_cfg.routing_enabled = 0x01; ud_cfg.rack_slot = (byte)(config.RoutingSlot + config.RoutingRack * 32); ud_cfg.size_of_subnet = 0x06; ud_cfg.routing_destination_1 = (byte)((config.RoutingSubnet1 >> 8) & 0xFF); ud_cfg.routing_destination_2 = (byte)((config.RoutingSubnet1) & 0xFF); ud_cfg.routing_destination_3 = (byte)((config.RoutingSubnet2 >> 8) & 0xFF); ud_cfg.routing_destination_4 = (byte)((config.RoutingSubnet2) & 0xFF); if (!config.RoutingToEthernet) { ud_cfg.size_of_routing_destination = 0x01; ud_cfg.routing_destination_1 = (byte)config.RoutingMPIAddres; ud_cfg.size_to_end = 0x09; } else { ud_cfg.size_of_routing_destination = 0x04; ud_cfg.routing_destination_1 = config.RoutingIPAddress.GetAddressBytes()[0]; ud_cfg.routing_destination_2 = config.RoutingIPAddress.GetAddressBytes()[1]; ud_cfg.routing_destination_3 = config.RoutingIPAddress.GetAddressBytes()[2]; ud_cfg.routing_destination_4 = config.RoutingIPAddress.GetAddressBytes()[3]; ud_cfg.size_to_end = 0x0C; } } ptr = Marshal.AllocHGlobal(Marshal.SizeOf(ud_cfg)); Marshal.StructureToPtr(ud_cfg, ptr, true); fdr.user_data_1 = new byte[260]; Marshal.Copy(ptr, fdr.user_data_1, 0, Marshal.SizeOf(ud_cfg)); Marshal.FreeHGlobal(ptr); SendData(fdr); rec = RecieveData(connNr); if (rec.response != 0x01) { throw new S7OnlineException("S7Online: Error Connection to PLC"); } #endregion #region Telegramm 5 (Ethernet 3) (this Telegramm sends a PDU) //5th Telegramm / TCP(3rd) Pdu pdu = new Pdu(1); pdu.Param.AddRange(new byte[] { 0xF0, 0, 0, 1, 0, 1, 3, 0xc0 }); SendPdu(pdu, retVal); Pdu recPdu = RecievePdu(connNr); #endregion #region Telegramm 6 (Ethernet 4) (get PDU size) fdr = new S7OexchangeBlock(); fdr.user = connNr;//0; fdr.subsystem = 64; fdr.opcode = 7; fdr.response = 16642; fdr.seg_length_1 = 480; fdr.application_block_opcode = retVal.application_block_opcode; fdr.application_block_subsystem = retVal.application_block_subsystem; SendData(fdr); recPdu = RecievePdu(connNr); retVal.PduSize = ByteFunctions.getU16from(recPdu.Param.ToArray(), 6); #endregion retVal.ConnectionEstablished = true; return(retVal); }
private Pdu RecievePdu(ushort myConnNr) { S7OexchangeBlock rec = RecieveData(myConnNr); return(new Pdu(rec.user_data_1)); }