Difference between revisions of "InSim examples"

From LFS Manual
Jump to navigationJump to search
m (Changed to meet with defacto standard as set on page.)
(5 intermediate revisions by 2 users not shown)
Line 5: Line 5:
 
How to connect, send a packet and receive the response.
 
How to connect, send a packet and receive the response.
  
<big><pre># Import Python's socket module.
+
<big><pre># Dependencies.
 
import socket
 
import socket
 +
import struct
  
# Import Python's struct module, which allows us to pack and unpack strings.
+
# Some constants.
import struct
+
INSIM_VERSION = 4
 +
BUFFER_SIZE = 2048
 +
 
 +
# Packet types.
 +
ISP_ISI = 1
 +
ISP_VER = 2
 +
ISP_TINY = 3
 +
TINY_NONE = 0
  
# Initialise the socket in TCP mode.  
+
# Initailise the socket in TCP mode.
 
sock = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
 
sock = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
  
Line 17: Line 25:
 
sock.connect(('localhost', 29999))
 
sock.connect(('localhost', 29999))
  
# Pack the IS_ISI data into a string.
+
# Pack the ISI packet into a string.
isi = struct.pack('BBBBHHBcH16s16s',  
+
isi = struct.pack('BBBBHHBBH16s16s',  
                   44,           # Size
+
                   44,         # Size
                   1,           # Type
+
                   ISP_ISI,     # Type
                   0,           # ReqI
+
                   1,           # ReqI - causes LFS to send an IS_VER.
                   0,           # Zero
+
                   0,           # Zero
                   0,           # UDPPort
+
                   0,           # UDPPort
                   0,           # Flags
+
                   0,           # Flags
                   0,           # Sp0
+
                   0,           # Sp0
                   ' ',         # Prefix
+
                   0,           # Prefix
                   0,           # Interval
+
                   0,           # Interval
                   'password',   # Admin
+
                   'password', # Admin  
                   'MyProgram',) # IName
+
                   '^3example') # IName
 
+
               
# Send the string to InSim
+
# Send the ISI packet to InSim.
 
sock.send(isi)
 
sock.send(isi)
  
 
# Some constants.
 
ISP_TINY = 3
 
TINY_NONE = 0
 
 
# keep alive the connection (see below)
 
def keepAlive(packet):
 
    # Check the packet type.
 
    if ord(packet[1]) == ISP_TINY:
 
        # Unpack the packet data.
 
        tiny = struct.unpack('BBBB', packet)
 
        # Check the SubT.
 
        if tiny[3] == TINY_NONE:
 
            # Send the keep alive packet back to LFS.
 
            sock.send(packet)
 
 
 
# We use a string as the buffer.
 
 
buffer = ''
 
buffer = ''
  
 
while True:
 
while True:
    # Receive up to 1024 bytes of data.
+
     data = sock.recv(BUFFER_SIZE)
     data = sock.recv(1024)
 
 
 
    # If no data is received the connection has closed.
 
 
     if data:
 
     if data:
        # Append received data onto the buffer.
 
 
         buffer += data
 
         buffer += data
 
+
       
         # Loop through each completed packet in the buffer. The first byte of
+
         # Loop through completed packets.
        # each packet is the packet size, so check that the length of the
 
        # buffer is at least the size of the first packet.  
 
 
         while len(buffer) > 0 and len(buffer) >= ord(buffer[0]):
 
         while len(buffer) > 0 and len(buffer) >= ord(buffer[0]):
 +
           
 
             # Copy the packet from the buffer.
 
             # Copy the packet from the buffer.
 
             packet = buffer[:ord(buffer[0])]
 
             packet = buffer[:ord(buffer[0])]
 +
            buffer = buffer[ord(buffer[0]):]
 +
           
 +
            # Check packet type.
 +
            if ord(buffer[1]) == ISP_TINY:
 +
                # Unpack the TINY packet and check it for keep-alive signal.
 +
                size, type, reqi, subt = struct.unpack('BBBB', packet)
 +
                if subt == TINY_NONE:
 +
                    sock.send(packet) # Respond to keep-alive.
 +
            elif ord(buffer[1]) == ISP_VER:
 +
                # Unpack the VER packet and check the InSim version.
 +
                size, type, reqi, _, version, product, insimver = struct.unpack('BBBB8s6sH')
 +
                if insimver != INSIM_VERSION:
 +
                    break # Invalid version, break loop.
 +
    else:
 +
        break # Connection has closed.
 +
       
 +
# Release the socket.
 +
sock.close()</pre></big>
  
             # Remove the packet from the buffer.
+
= Visual C# =
            buffer = buffer[ord(buffer[0]):]
+
 
 +
== Example #1 ==
 +
 
 +
How to connect, send a packet and receive the response.
 +
 
 +
<big><pre>using System;
 +
using System.Collections.Generic;
 +
using System.Net;
 +
using System.Net.Sockets;
 +
using System.Text;
 +
 
 +
class Program
 +
{
 +
    enum PacketType
 +
    {
 +
        ISP_ISI = 0,
 +
        ISP_VER = 1,
 +
        ISP_TINY = 2,
 +
    }
 +
 
 +
    enum TinyType
 +
    {
 +
        TINY_NONE = 0,
 +
    }
 +
 
 +
    const int BufferSize = 2048;
 +
    const int InSimVersion = 4;
 +
 
 +
    static void Main()
 +
    {
 +
        // Initailise the Socket and connect to InSim.
 +
        Socket sock = new Socket(
 +
            AddressFamily.InterNetwork,
 +
             SocketType.Stream,
 +
            ProtocolType.Tcp);
 +
        sock.Connect("localhost", 29999);
 +
 
 +
        // Create the ISI packet.
 +
        byte[] isi = new byte[44];
 +
        isi[0] = 44; // Size
 +
        isi[1] = (byte)PacketType.ISP_ISI; // Type
 +
        isi[2] = 1; // ReqI
 +
        isi[3] = 0; // Zero
 +
        isi[4] = 0; // UDPPort
 +
        isi[5] = 0; // UDPPort
 +
        isi[6] = 0; // Flags
 +
        isi[7] = 0; // Flags
 +
        isi[8] = 0; // Sp0
 +
        isi[9] = (byte)'!'; // Prefix
 +
        isi[10] = 0; // Interval
 +
        isi[11] = 0; // Interval
 +
        ASCIIEncoding.ASCII.GetBytes("password", 0, 8, isi, 12); // Admin
 +
        ASCIIEncoding.ASCII.GetBytes("^3Example", 0, 9, isi, 28); // IName
 +
 
 +
        // Send the packet to InSim.
 +
        sock.Send(isi);
 +
 
 +
        // Packet buffer.
 +
        List<byte> buffer = new List<byte>();
 +
 
 +
        while (true)
 +
        {
 +
            // Receive data from socket.
 +
            byte[] data = new byte[BufferSize];
 +
            int received = sock.Receive(data);
 +
            if (received > 0)
 +
            {
 +
                // Add the data to the packet buffer.
 +
                byte[] temp = new byte[received];
 +
                Array.Copy(data, temp, received);
 +
                buffer.AddRange(temp);
 +
 
 +
                // Loop through all packets in the buffer.
 +
                while (buffer.Count > 0 && buffer.Count >= buffer[0])
 +
                {
 +
                    // Copy packet from buffer.
 +
                    byte[] packet = new byte[buffer[0]];
 +
                    buffer.CopyTo(0, packet, 0, buffer[0]);
 +
                    buffer.RemoveRange(0, buffer[0]);
 +
 
 +
                    // Check packet type.
 +
                    if (PacketType.ISP_TINY == (PacketType)buffer[1])
 +
                    {
 +
                        // Unpack TINY and respond to keep-alive.
 +
                        byte size = packet[0];
 +
                        PacketType type = (PacketType)packet[1];
 +
                        byte reqi = packet[2];
 +
                        TinyType subt = (TinyType)packet[3];
 +
 
 +
                        if (subt == TinyType.TINY_NONE)
 +
                        {
 +
                            sock.Send(packet);
 +
                        }
 +
                    }
 +
                    else if (PacketType.ISP_VER == (PacketType)buffer[1])
 +
                    {
 +
                        // Unpack VER and check InSim version.
 +
                        byte size = packet[0];
 +
                        PacketType type = (PacketType)packet[1];
 +
                        byte reqi = packet[2];
 +
                        byte zero = packet[3];
 +
                        string version = ASCIIEncoding.ASCII.GetString(packet, 4, 8);
 +
                        string product = ASCIIEncoding.ASCII.GetString(packet, 12, 6);
 +
                        ushort insimver = BitConverter.ToUInt16(packet, 18);
 +
 
 +
                        if (insimver != InSimVersion)
 +
                        {
 +
                            break;
 +
                        }
 +
                    }
 +
                }
 +
            }
 +
            else
 +
            {
 +
                // Connection has closed.
 +
                break;
 +
            }
 +
        }
  
            # check keep alive!
+
        // Release the socket.
            keepAlive(packet)
+
        sock.Close();
 +
    }
 +
}
  
            # The packet is now complete! :)
+
</pre></big>
            # doSomethingWithPacket(packet)
 
    else:
 
        break
 
  
# Release the socket.
+
= PHP =
sock.close()</pre></big>
+
== Example #1 ==
 +
<big><pre><?php
 +
$InSim = new InSim();
 +
class InSim {
 +
    function __construct($AdminPass = '', $Address = '127.0.0.1', $Port = 29999, $PreFixChar = '!') {
 +
        // Socket In;
 +
        if ($this->skIn = socket_create(AF_INET, SOCK_DGRAM, SOL_UDP)) {
 +
            echo('Listen socket created!' . PHP_EOL);
 +
            if (socket_bind($this->skIn, $Address, $Port + 1))
 +
                echo('Binded to listen socket!' . PHP_EOL);
 +
            else
 +
                die('Could not bind to listen socket, address or port!' . PHP_EOL);
 +
        } else
 +
            die('Could not create listen socket!' . PHP_EOL);
 +
       
 +
        // Socket Out;
 +
        if ($this->skOt = socket_create(AF_INET, SOCK_DGRAM, SOL_UDP)) {
 +
            echo('Send socket created!' . PHP_EOL);
 +
            if (socket_connect($this->skOt, $Address, $Port))
 +
                echo('Conneceted to send socket!' . PHP_EOL);
 +
            else
 +
                die('Could not connect to send socket, address or port!' . PHP_EOL);
 +
        } else
 +
            die('Could not create send socket!');
 +
       
 +
        # Connect To InSim;
 +
        $this->send(pack('CCCxSSxCSa16a16', 44, 1, 1, $Port + 1, 4 | 8, 36, 0, $AdminPass, 'phpInSim'));
 +
        $this->main();
 +
    }
 +
    function send($packet) {
 +
        return socket_write($this->skOt, $packet, strlen($packet));
 +
    }
 +
    function main() {
 +
        while (TRUE) {
 +
            # Keep Alive;
 +
            if (time() > $this->time) {
 +
                $this->send(pack('CCCC', 4, 3, 0, 0));
 +
                $this->time = time() + 30;
 +
            }
 +
            # Get Packet;
 +
            if ($data = $this->recv()) {
 +
                print_r($data);
 +
            }
 +
        }
 +
    }
 +
    function recv() {
 +
        return socket_read($this->skIn, 256, PHP_BINARY_READ);
 +
    }
 +
    function __destruct() {
 +
        $this->send(pack('CCCC', 4, 3, 0, 2));
 +
    }
 +
}
 +
?></pre></big>

Revision as of 09:35, 17 July 2009

Python

Example #1

How to connect, send a packet and receive the response.

# Dependencies.
import socket
import struct

# Some constants.
INSIM_VERSION = 4
BUFFER_SIZE = 2048

# Packet types.
ISP_ISI = 1
ISP_VER = 2
ISP_TINY = 3
TINY_NONE = 0

# Initailise the socket in TCP mode.
sock = socket.socket(socket.AF_INET, socket.SOCK_STREAM)

# Connect to LFS.
sock.connect(('localhost', 29999))

# Pack the ISI packet into a string.
isi = struct.pack('BBBBHHBBH16s16s', 
                  44,          # Size
                  ISP_ISI,     # Type
                  1,           # ReqI - causes LFS to send an IS_VER. 
                  0,           # Zero
                  0,           # UDPPort
                  0,           # Flags
                  0,           # Sp0
                  0,           # Prefix
                  0,           # Interval
                  'password',  # Admin 
                  '^3example') # IName
                 
# Send the ISI packet to InSim. 
sock.send(isi)

buffer = ''

while True:
    data = sock.recv(BUFFER_SIZE)
    if data:
        buffer += data
        
        # Loop through completed packets.
        while len(buffer) > 0 and len(buffer) >= ord(buffer[0]):
            
            # Copy the packet from the buffer.
            packet = buffer[:ord(buffer[0])]
            buffer = buffer[ord(buffer[0]):]
            
            # Check packet type.
            if ord(buffer[1]) == ISP_TINY:
                # Unpack the TINY packet and check it for keep-alive signal.
                size, type, reqi, subt = struct.unpack('BBBB', packet)
                if subt == TINY_NONE:
                    sock.send(packet) # Respond to keep-alive.
            elif ord(buffer[1]) == ISP_VER:
                # Unpack the VER packet and check the InSim version.
                size, type, reqi, _, version, product, insimver = struct.unpack('BBBB8s6sH')
                if insimver != INSIM_VERSION:
                    break # Invalid version, break loop.
    else: 
        break # Connection has closed.
        
# Release the socket.
sock.close()

Visual C#

Example #1

How to connect, send a packet and receive the response.

using System;
using System.Collections.Generic;
using System.Net;
using System.Net.Sockets;
using System.Text;

class Program
{
    enum PacketType
    {
        ISP_ISI = 0,
        ISP_VER = 1,
        ISP_TINY = 2,
    }

    enum TinyType
    {
        TINY_NONE = 0,
    }

    const int BufferSize = 2048;
    const int InSimVersion = 4;

    static void Main()
    {
        // Initailise the Socket and connect to InSim.
        Socket sock = new Socket(
            AddressFamily.InterNetwork,
            SocketType.Stream,
            ProtocolType.Tcp);
        sock.Connect("localhost", 29999);

        // Create the ISI packet.
        byte[] isi = new byte[44];
        isi[0] = 44; // Size
        isi[1] = (byte)PacketType.ISP_ISI; // Type
        isi[2] = 1; // ReqI
        isi[3] = 0; // Zero
        isi[4] = 0; // UDPPort
        isi[5] = 0; // UDPPort
        isi[6] = 0; // Flags
        isi[7] = 0; // Flags
        isi[8] = 0; // Sp0
        isi[9] = (byte)'!'; // Prefix
        isi[10] = 0; // Interval
        isi[11] = 0; // Interval
        ASCIIEncoding.ASCII.GetBytes("password", 0, 8, isi, 12); // Admin
        ASCIIEncoding.ASCII.GetBytes("^3Example", 0, 9, isi, 28); // IName

        // Send the packet to InSim.
        sock.Send(isi);

        // Packet buffer.
        List<byte> buffer = new List<byte>();

        while (true)
        {
            // Receive data from socket.
            byte[] data = new byte[BufferSize];
            int received = sock.Receive(data);
            if (received > 0)
            {
                // Add the data to the packet buffer.
                byte[] temp = new byte[received];
                Array.Copy(data, temp, received);
                buffer.AddRange(temp);

                // Loop through all packets in the buffer.
                while (buffer.Count > 0 && buffer.Count >= buffer[0])
                {
                    // Copy packet from buffer.
                    byte[] packet = new byte[buffer[0]];
                    buffer.CopyTo(0, packet, 0, buffer[0]);
                    buffer.RemoveRange(0, buffer[0]);

                    // Check packet type.
                    if (PacketType.ISP_TINY == (PacketType)buffer[1])
                    {
                        // Unpack TINY and respond to keep-alive.
                        byte size = packet[0];
                        PacketType type = (PacketType)packet[1];
                        byte reqi = packet[2];
                        TinyType subt = (TinyType)packet[3];

                        if (subt == TinyType.TINY_NONE)
                        {
                            sock.Send(packet);
                        }
                    }
                    else if (PacketType.ISP_VER == (PacketType)buffer[1])
                    {
                        // Unpack VER and check InSim version.
                        byte size = packet[0];
                        PacketType type = (PacketType)packet[1];
                        byte reqi = packet[2];
                        byte zero = packet[3];
                        string version = ASCIIEncoding.ASCII.GetString(packet, 4, 8);
                        string product = ASCIIEncoding.ASCII.GetString(packet, 12, 6);
                        ushort insimver = BitConverter.ToUInt16(packet, 18);

                        if (insimver != InSimVersion)
                        {
                            break;
                        }
                    }
                }
            }
            else
            {
                // Connection has closed.
                break;
            }
        }

        // Release the socket.
        sock.Close();
    }
}

PHP

Example #1

<?php
$InSim = new InSim();
class InSim {
    function __construct($AdminPass = '', $Address = '127.0.0.1', $Port = 29999, $PreFixChar = '!') {
        // Socket In;
        if ($this->skIn = socket_create(AF_INET, SOCK_DGRAM, SOL_UDP)) {
            echo('Listen socket created!' . PHP_EOL);
            if (socket_bind($this->skIn, $Address, $Port + 1))
                echo('Binded to listen socket!' . PHP_EOL);
            else
                die('Could not bind to listen socket, address or port!' . PHP_EOL);
        } else
            die('Could not create listen socket!' . PHP_EOL);
        
        // Socket Out;
        if ($this->skOt = socket_create(AF_INET, SOCK_DGRAM, SOL_UDP)) {
            echo('Send socket created!' . PHP_EOL);
            if (socket_connect($this->skOt, $Address, $Port))
                echo('Conneceted to send socket!' . PHP_EOL);
            else
                die('Could not connect to send socket, address or port!' . PHP_EOL);
        } else
            die('Could not create send socket!');
        
        # Connect To InSim;
        $this->send(pack('CCCxSSxCSa16a16', 44, 1, 1, $Port + 1, 4 | 8, 36, 0, $AdminPass, 'phpInSim'));
        $this->main();
    }
    function send($packet) {
        return socket_write($this->skOt, $packet, strlen($packet));
    }
    function main() {
        while (TRUE) {
            # Keep Alive;
            if (time() > $this->time) {
                $this->send(pack('CCCC', 4, 3, 0, 0));
                $this->time = time() + 30;
            }
            # Get Packet;
            if ($data = $this->recv()) {
                print_r($data);
            }
        }
    }
    function recv() {
        return socket_read($this->skIn, 256, PHP_BINARY_READ);
    }
    function __destruct() {
        $this->send(pack('CCCC', 4, 3, 0, 2));
    }
}
?>