// receive thread private void ReceiveData() { client = new UdpClient(port); while (true) { try { // Bytes received IPEndPoint clientEndpoint = new IPEndPoint(IPAddress.Any, 0); byte[] data = client.Receive(ref clientEndpoint); lastClientIP = clientEndpoint.Address.ToString(); lastClientPort = clientEndpoint.Port; if (data.Length == 4) // if the packet received is not equal to 4 bytes (32 bits), the packet is discarded { // The action of creating or updating the weapons happens in the main thread. Action <IPEndPoint, byte[]> action = new Action <IPEndPoint, byte[]>(CreateScar); //The action is created dispatcher.Invoke(action, clientEndpoint, data); // The action is send to the dispatcher to be executed in the main thread (UDPServer.Update()) // Convert bytes in a string lastUDPdecoded = Encoding.UTF8.GetString(data); // Gives a hex representation of the data in String form dataString = ByteArrayToString(data); // gives a hex representation of the data (handy for debugging purposes) // Log data in .txt file textIO.WriteTextFile(lastClientIP, dataString); } } catch (Exception err) { print(err.ToString()); } } }
// Translate the data and edit the parameters of the virtual weapon public void PacketTranslater(byte[] packet) // if reading problems occur, this can be due to the endian (the sequence in which the bits are send, LSB first or last?) { // Check if the data is still send by the same type of weapon. It should be impossible for a weapon to change type (this is just in case) // If the client keeps sending packets with the wrong weapontype tag, it will be considered as inactive and the weapon will get deleted after a certain time if (GetWeaponTypeOutOfData(packet) == weaponType) { // Create storage containers byte[] triggerValue = new byte[4]; byte[] movablePiecesValue = new byte[4]; byte[] magazineIDValue = new byte[4]; byte[] flags = new byte[4]; // Store data in containers Array.Copy(packet, 0, triggerValue, 0, 1); //Copy(Array sourceArray, long sourceIndex, Array destinationArray, long destinationIndex, long length) Array.Copy(packet, 1, movablePiecesValue, 0, 1); Array.Copy(packet, 2, magazineIDValue, 0, 1); Array.Copy(packet, 3, flags, 0, 1); // Set current values triggerCurrentValue = BitConverter.ToInt32(triggerValue, 0); movablePiecesCurrentValue = BitConverter.ToInt32(movablePiecesValue, 0);// BitConverter start reading at a certain index till the end. magazineID = BitConverter.ToInt32(magazineIDValue, 0); byte flagByte = flags[0]; magazinePresent = !(flagByte % 2 == 0); // Last bit in the flag byte shows the mag status. So, if there is no mag present the value of the flag is even. byte switchPositionByte = (byte)(flagByte * Math.Pow(2, weaponTypesBits)); // bit shift left the enough of times to get rid of the used MSB's to encode the weapontype switchPositionByte /= (byte)Math.Pow(2, weaponTypesBits + 1); // BSR enough times to set the bits needed to recognize the selector switches position as LSB's selectorSwitchPosition = (SwitchPosition)switchPositionByte; // Create list data to be written in a textfile ArrayList dataArrayList = new ArrayList { triggerCurrentValue, selectorSwitchPosition, movablePiecesCurrentValue, magazinePresent, magazineID }; textIO.WriteTextFile(dataArrayList); lastUpdate = DateTime.Now;// Use of this has to be reconsidered => it takes too much time } }