├── .idea
├── .gitignore
├── inspectionProfiles
│ └── profiles_settings.xml
└── misc.xml
├── README.md
├── client.go
├── config.go
├── connection.go
├── datagram_builder.go
├── default_handlers.go
├── host.go
├── info
└── info.go
├── logger.go
├── minecraft_batch_packet.go
├── packet_handler.go
├── packets
├── add_entity_packet.go
├── add_player_packet.go
├── interact_packet.go
├── inventory_transaction_packet.go
├── inventoryio
│ ├── inventory_action_io.go
│ ├── inventory_action_io_list.go
│ └── stream
│ │ └── inventory_action_stream.go
├── modal_form_request_packet.go
├── modal_form_response_packet.go
├── move_entity_packet.go
├── move_player_packet.go
├── remove_entity_packet.go
├── set_game_mode_packet.go
├── set_title_packet.go
├── text_packet.go
└── update_attributes_packet.go
├── proxy.go
├── reliability.go
├── server.go
├── server_data.go
└── start
└── main.go
/.idea/.gitignore:
--------------------------------------------------------------------------------
1 | # Default ignored files
2 | /shelf/
3 | /workspace.xml
4 | # Editor-based HTTP Client requests
5 | /httpRequests/
6 | # Datasource local storage ignored files
7 | /dataSources/
8 | /dataSources.local.xml
9 |
--------------------------------------------------------------------------------
/.idea/inspectionProfiles/profiles_settings.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
--------------------------------------------------------------------------------
/.idea/misc.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
--------------------------------------------------------------------------------
/README.md:
--------------------------------------------------------------------------------
1 | # GoProxy (broken and outdated)
2 |
3 | ### GoProxy is a man-in-the-middle (MITM) proxy, it works by intercepting and modifying packets between the client and the server.
4 |
5 | ### How to use
6 |
7 | To use you must have Go version 1.9 or greater installed.
8 |
9 | 1. clone the project: `go get github.com/InfinityGamers/GoProxy`
10 | 2. navigate to the clone directory
11 | 3. install dependencies with `go install`
12 | 4. compile it and run it
13 | # Example use cases
14 | ### In this case it was mainly used to have advantages in Minecraft.
15 |
16 | ## KILLAURA CHEATS
17 | [](https://www.youtube.com/watch?v=w4J-HzICmWc)
18 | ## SPEED/KILLAURA/FLYING CHEATS
19 | [](https://www.youtube.com/watch?v=h43zbAWX7zQ)
20 | ## AUTOMATED MINECRAFT PVP BOT
21 | [](https://www.youtube.com/watch?v=2NqTOBOu0-Y)
22 |
23 | ### Notices
24 |
25 | This will not work on encrypted servers such as LBSG, Mineplex, etc.
26 | At the moment it has very simple features, but I will continue on updating as much as I can.
--------------------------------------------------------------------------------
/client.go:
--------------------------------------------------------------------------------
1 | package goproxy
2 |
3 | import (
4 | "net"
5 | "github.com/infinitygamers/goproxy/packets"
6 | "github.com/google/uuid"
7 | packets2 "github.com/Irmine/GoMine/net/packets"
8 | "time"
9 | "github.com/golang/geo/r3"
10 | )
11 |
12 | type Client struct {
13 | Host // Server extends a host that has writable packets
14 | // Server's udp address
15 | addr net.UDPAddr
16 | // the main Proxy
17 | Proxy *Proxy
18 | // the Connection between the Server
19 | // and the Client
20 | Conn *Connection
21 | // a bool that is true if the Client
22 | // is connected with the Server/Proxy
23 | Connection bool
24 | // the UUID of the Client's player
25 | uuid uuid.UUID
26 | // the entity runtime id of
27 | // the Client's player
28 | //entityRuntimeID uint64
29 | // the Client's position in the level
30 | Position r3.Vector
31 | }
32 |
33 | // returns new Client host
34 | // that has writable packets
35 | func NewClient(proxy *Proxy, conn *Connection) *Client {
36 | client := Client{}
37 | client.Proxy = proxy
38 | client.Conn = conn
39 | client.Connection = false
40 | return &client
41 | }
42 |
43 | // returns if this host is the client
44 | // this is the client struct to it returns true
45 | func (client Client) IsClient() bool {
46 | return true
47 | }
48 |
49 | // returns if this host is the client
50 | // this is the client struct to it returns false
51 | func (client Client) IsServer() bool {
52 | return false
53 | }
54 |
55 | // this function is from the host interface
56 | // it writes a packet buffer to the Client
57 | func (client Client) WritePacket(buffer []byte) {
58 | _, err := client.Proxy.UDPConn.WriteTo(buffer, &client.addr)
59 | if err != nil {
60 | Alert(err.Error())
61 | }
62 | }
63 |
64 | // this function is from the host interface
65 | // This sends a single packet
66 | func (client Client) SendPacket(packet packets2.IPacket) {
67 | client.SendBatchPacket([]packets2.IPacket{packet})
68 | }
69 |
70 | // this function is from the host interface
71 | // it sends a batch packet:
72 | // a packet with multiple packets inside
73 | func (client Client) SendBatchPacket(packets []packets2.IPacket) {
74 | datagram := client.Conn.pkHandler.DatagramBuilder.BuildFromPackets(packets)
75 | client.WritePacket(datagram.Buffer)
76 | }
77 |
78 | // this set's the udp address
79 | // which is used to communicate with the Client
80 | func (client *Client) SetAddress(addr net.UDPAddr) {
81 | client.addr = addr
82 | }
83 |
84 | // returns the Client's address as net.UDPAddr
85 | func (client Client) GetAddress() net.UDPAddr {
86 | return client.addr
87 | }
88 |
89 | // set true if the Client is connected with the
90 | // Server/Proxy
91 | func (client *Client) SetConnected(b bool) {
92 | client.Connection = b
93 | }
94 |
95 | // returns true if the Client is connected with the
96 | // Server/Proxy
97 | func (client *Client) IsConnected() bool {
98 | return client.Connection
99 | }
100 |
101 | // sends the Client's player a string message
102 | func (client *Client) SendMessage(m string) {
103 | text := packets.NewTextPacket()
104 | text.Message = m
105 | client.SendPacket(text)
106 | }
107 |
108 | // changes the Client's player game mode
109 | // although it updates for the Client, it will
110 | // not on the Server's side
111 | func (client *Client) SetGameMode(g int32) {
112 | gm := packets.NewSetGamemodePacket()
113 | gm.GameMode = g
114 | client.Conn.Server.SendPacket(gm)
115 | client.SendPacket(gm)
116 | }
117 |
118 | // Set a screen title and subtitle to the Client
119 | func (client *Client) SetTitle(title, subtitle string, fadeInTime, stayTime, fadeOutTime int32) {
120 | // title
121 | t := packets.NewSetTitlePacket()
122 | t.TitleType = packets.SetTitle
123 | t.Text = title
124 | t.FadeInTime = fadeInTime
125 | t.StayTime = stayTime
126 | t.FadeOutTime = fadeOutTime
127 |
128 | // subtitle
129 | t2 := packets.NewSetTitlePacket()
130 | t2.TitleType = packets.SetSubtitle
131 | t2.Text = subtitle
132 | t2.FadeInTime = fadeInTime
133 | t2.StayTime = stayTime
134 | t2.FadeOutTime = fadeOutTime
135 |
136 | client.SendBatchPacket([]packets2.IPacket{t, t2})
137 | }
138 |
139 | func (client *Client) SendJoinMessage() {
140 | go func() {
141 | time.Sleep(5 * time.Second)
142 | client.SendMessage(BrightBlue + "==============================")
143 | client.SendMessage(BrightGreen + Prefix + Orange + "You are using " + Author + "'s Proxy version " + Version)
144 | client.SendMessage(BrightBlue + "==============================")
145 | client.SetTitle(BrightGreen + Author + "'s Proxy", Orange + Author + "'s Proxy version " + Version, 1, 1, 1)
146 | }()
147 | }
--------------------------------------------------------------------------------
/config.go:
--------------------------------------------------------------------------------
1 | package goproxy
2 |
3 | import (
4 | "os"
5 | "gopkg.in/yaml.v2"
6 | "io/ioutil"
7 | )
8 |
9 | type Config struct {
10 |
11 | ServerAddr string `yaml:"Server-address"`
12 | ServerPort int `yaml:"Server-port"`
13 | BindAddr string `yaml:"bind-address"`
14 | BindPort int `yaml:"bind-port"`
15 |
16 | }
17 |
18 | func NewConfig() Config {
19 |
20 | if _, err := os.Stat("./config.yml"); os.IsNotExist(err) {
21 | o, _ := yaml.Marshal(Config{
22 | ServerAddr: "0.0.0.0",
23 | ServerPort: 19132,
24 | BindAddr: "0.0.0.0",
25 | BindPort: 19133,
26 |
27 | })
28 | f, err := os.OpenFile("./config.yml", os.O_APPEND | os.O_CREATE | os.O_WRONLY, 0644)
29 | if err != nil {
30 | panic(err)
31 | }
32 | _, err = f.WriteString(string(o))
33 | if err != nil {
34 | panic(err)
35 | }
36 | f.Close()
37 | }
38 |
39 | var config Config
40 | yaml2, _ := ioutil.ReadFile("./config.yml")
41 | yaml.Unmarshal(yaml2, &config)
42 |
43 | return config
44 | }
45 |
--------------------------------------------------------------------------------
/connection.go:
--------------------------------------------------------------------------------
1 | package goproxy
2 |
3 | import (
4 | "net"
5 | "github.com/Irmine/GoRakLib/protocol"
6 | )
7 |
8 | const (
9 | IdUnconnectedPingOpenConnection = 0x01 //Client to Server
10 | IdUnconnectedPongOpenConnection = 0x1c //Server to Client as response to IdConnectedPingOpenConnection (0x01)
11 | IdOpenConnectionRequest1 = 0x05 //Client to Server
12 | IdOpenConnectionReply1 = 0x06 //Server to Client
13 | IdOpenConnectionRequest2 = 0x07 //Client to Server
14 | IdOpenConnectionReply2 = 0x08 //Server to Client
15 | )
16 |
17 | type Connection struct {
18 | Proxy *Proxy
19 | Client *Client
20 | Server *Server
21 | pkHandler *PacketHandler
22 | }
23 |
24 | func NewConnection(proxy *Proxy) Connection {
25 | conn := Connection{}
26 | conn.Proxy = proxy
27 |
28 | conn.Client = NewClient(proxy, &conn)
29 | conn.Server = NewServer(proxy, &conn)
30 | conn.pkHandler = NewPacketHandler()
31 |
32 | conn.pkHandler.Conn = &conn
33 |
34 | RegisterDefaultHandlers(conn.pkHandler)
35 |
36 | return conn
37 | }
38 |
39 | func (conn *Connection) GetClient() *Client {
40 | return conn.Client
41 | }
42 |
43 | func (conn *Connection) GetServer() *Server {
44 | return conn.Server
45 | }
46 |
47 | func (conn *Connection) GetPacketHandler() *PacketHandler {
48 | return conn.pkHandler
49 | }
50 |
51 | func (conn *Connection) IsClient(addr net.UDPAddr) bool {
52 | return conn.Client.addr.IP.Equal(addr.IP)
53 | }
54 |
55 | func (conn *Connection) IsServer(addr net.UDPAddr) bool {
56 | return conn.Server.GetAddress().IP.Equal(addr.IP)
57 | }
58 |
59 | func (conn *Connection) handleUnconnectedPing(addr net.UDPAddr, buffer []byte) {
60 | conn.Client.SetAddress(addr)
61 | conn.Server.WritePacket(buffer)
62 |
63 | //stringAddr := addr.IP.String()
64 | //Info("Received unconnected ping from Client address: " + stringAddr)
65 | }
66 |
67 | func (conn *Connection) handleUnconnectedPong(addr net.UDPAddr, buffer []byte) {
68 | pk := protocol.NewUnconnectedPong()
69 | pk.SetBuffer(buffer)
70 | pk.Decode()
71 | pk.Encode()
72 |
73 | conn.Client.WritePacket(pk.Buffer)
74 | conn.Server.Data.ParseFromString(pk.PongData)
75 |
76 | //stringAddr := addr.IP.String()
77 | //Info("Received unconnected pong from Server address: " + stringAddr)
78 | }
79 |
80 | func (conn *Connection) handleConnectionRequest1(addr net.UDPAddr, buffer []byte) {
81 | conn.Client.SetAddress(addr)
82 | conn.Server.WritePacket(buffer)
83 |
84 | //stringAddr := addr.IP.String()
85 | //
86 | //Info("Received Connection request 1 from Client address: " + stringAddr)
87 | }
88 |
89 | func (conn *Connection) handleConnectionReply1(addr net.UDPAddr, buffer []byte) {
90 | //stringAddr := addr.IP.String()
91 | //Info("Received Connection reply 1 from Server address: " + stringAddr)
92 |
93 | pk := protocol.NewOpenConnectionReply1()
94 | pk.SetBuffer(buffer)
95 | pk.Decode()
96 | pk.Encode()
97 |
98 | conn.Client.WritePacket(pk.Buffer)
99 | }
100 |
101 | func (conn *Connection) handleConnectionRequest2(addr net.UDPAddr, buffer []byte) {
102 | conn.Client.SetAddress(addr)
103 | conn.Server.WritePacket(buffer)
104 |
105 | //stringAddr := addr.IP.String()
106 | //
107 | //Info("Received Connection request 2 from Client address: " + stringAddr)
108 | }
109 |
110 | func (conn *Connection) handleConnectionReply2(addr net.UDPAddr, buffer []byte) {
111 | conn.Client.SetConnected(true)
112 |
113 | //stringAddr := addr.IP.String()
114 | //Info("Received Connection reply 2 from Server address: " + stringAddr)
115 |
116 | pk := protocol.NewOpenConnectionReply2()
117 | pk.SetBuffer(buffer)
118 | pk.Decode()
119 |
120 | pk.Encode()
121 |
122 | conn.Client.WritePacket(pk.Buffer)
123 | }
124 |
125 | func (conn *Connection) HandleIncomingPackets() {
126 | for {
127 | buffer := make([]byte, 2048)
128 | _, addr, err := conn.Proxy.UDPConn.ReadFromUDP(buffer)
129 |
130 | if err != nil {
131 | Alert(err.Error())
132 | continue
133 | }
134 |
135 | MessageId := buffer[0]
136 |
137 | if conn.Client.IsConnected() {
138 | if conn.IsServer(*addr) {
139 | conn.pkHandler.HandleIncomingPacket(buffer, conn.Client, *addr)
140 | } else {
141 | conn.pkHandler.HandleIncomingPacket(buffer, conn.Server, *addr)
142 | }
143 | continue
144 | }
145 |
146 | switch MessageId {
147 | case byte(IdUnconnectedPingOpenConnection):
148 | conn.handleUnconnectedPing(*addr, buffer)
149 | break
150 | case byte(IdUnconnectedPongOpenConnection):
151 | conn.handleUnconnectedPong(*addr, buffer)
152 | break
153 | case byte(IdOpenConnectionRequest1):
154 | conn.handleConnectionRequest1(*addr, buffer)
155 | break
156 | case byte(IdOpenConnectionReply1):
157 | conn.handleConnectionReply1(*addr, buffer)
158 | break
159 | case byte(IdOpenConnectionRequest2):
160 | conn.handleConnectionRequest2(*addr, buffer)
161 | break
162 | case byte(IdOpenConnectionReply2):
163 | conn.handleConnectionReply2(*addr, buffer)
164 | break
165 | }
166 | }
167 | }
--------------------------------------------------------------------------------
/datagram_builder.go:
--------------------------------------------------------------------------------
1 | package goproxy
2 |
3 | import (
4 | "github.com/Irmine/GoMine/net/packets"
5 | "github.com/Irmine/GoRakLib/protocol"
6 | )
7 |
8 | // DatagramBuilds builds datagram
9 | // either from a packet or from raw bytes
10 | // datagrams are the communication method
11 | // for the RakNet protocol
12 | type DatagramBuilder struct {
13 | pkHandler *PacketHandler
14 | }
15 |
16 | func NewDatagramBuilder() DatagramBuilder {
17 | return DatagramBuilder{}
18 | }
19 |
20 | // this builds a datagram from packets
21 | // with the encode/decode function
22 | // and sets the order of the datagram
23 | // to the Proxy's own sequence number order
24 | func (db *DatagramBuilder) BuildFromPackets(packets []packets.IPacket) protocol.Datagram {
25 | db.pkHandler.orders.SequenceNumber++
26 | datagram := db.BuildRawFromPackets(packets, Unreliable, db.pkHandler.orders.SequenceNumber, 0, 0)
27 | return datagram
28 | }
29 |
30 | // this builds a datagram from raw bytes
31 | // and sets the order of the datagram
32 | // to the Proxy's own sequence number order
33 | func (db *DatagramBuilder) BuildFromBuffer(packets []byte) protocol.Datagram {
34 | db.pkHandler.orders.SequenceNumber++
35 | datagram := db.BuildRaw(append([][]byte{}, packets), Unreliable, db.pkHandler.orders.SequenceNumber, 0, 0)
36 | return datagram
37 | }
38 |
39 | // this builds a datagram from packets
40 | // with the encode/decode function
41 | // and sets the order of the datagram
42 | // to the latest sequence number received
43 | func (db *DatagramBuilder) BuildFromPacketsWithLatestSequence(packets []packets.IPacket) protocol.Datagram {
44 | db.pkHandler.lastSequenceNumber++
45 | datagram := db.BuildRawFromPackets(packets, Unreliable, db.pkHandler.lastSequenceNumber, 0, 0)
46 | return datagram
47 | }
48 |
49 | // this builds a datagram from raw bytes
50 | // and sets the order of the datagram
51 | // to the latest sequence number received
52 | func (db *DatagramBuilder) BuildFromBufferWithLatestSequence(packets []byte) protocol.Datagram {
53 | db.pkHandler.lastSequenceNumber++
54 | datagram := db.BuildRaw(append([][]byte{}, packets), Unreliable, db.pkHandler.lastSequenceNumber, 0, 0)
55 | return datagram
56 | }
57 |
58 |
59 | // this builds a datagram from a packet batch
60 | // and sets the reliability of the encapsulated
61 | // packet to a custom one and the order of the
62 | // datagram to a custom sequence number
63 | func (db *DatagramBuilder) BuildFromBatch(batch *MinecraftPacketBatch, reliability byte, sequenceNumber, orderIndex, messageIndex uint32) protocol.Datagram {
64 | encapsulated := protocol.NewEncapsulatedPacket()
65 | encapsulated.Reliability = reliability
66 | encapsulated.OrderIndex = orderIndex
67 | encapsulated.MessageIndex = messageIndex
68 | encapsulated.Buffer = batch.Buffer
69 | datagram := protocol.NewDatagram()
70 | datagram.SequenceNumber = sequenceNumber
71 | datagram.AddPacket(encapsulated)
72 | datagram.Encode()
73 | return *datagram
74 | }
75 |
76 | // this builds a datagram from a slice
77 | // of encapsulated packets and sets the
78 | // reliability of the encapsulated packet
79 | // to a custom one and the order of the
80 | // datagram to a custom sequence number
81 | func (db *DatagramBuilder) BuildFromEncapsulated(packets []*protocol.EncapsulatedPacket, sequenceNumber uint32) protocol.Datagram {
82 | datagram := protocol.NewDatagram()
83 | datagram.SequenceNumber = sequenceNumber
84 | for _, p := range packets {
85 | datagram.AddPacket(p)
86 | }
87 | datagram.Encode()
88 | return *datagram
89 | }
90 |
91 | // this builds a datagram from raw bytes
92 | // and sets the reliability of the
93 | // encapsulated packet to a custom one
94 | // and the order of the datagram
95 | // to a custom sequence number
96 | func (db *DatagramBuilder) BuildRaw(packets [][]byte, reliability byte, sequenceNumber, orderIndex, messageIndex uint32) protocol.Datagram {
97 | batch := NewMinecraftPacketBatch()
98 | batch.rawPackets = packets
99 | batch.Encode()
100 | encapsulated := protocol.NewEncapsulatedPacket()
101 | encapsulated.Reliability = reliability
102 | encapsulated.OrderIndex = orderIndex
103 | encapsulated.MessageIndex = messageIndex
104 | encapsulated.Buffer = batch.Buffer
105 | datagram := protocol.NewDatagram()
106 | datagram.SequenceNumber = sequenceNumber
107 | datagram.AddPacket(encapsulated)
108 | datagram.Encode()
109 | return *datagram
110 | }
111 |
112 | // this builds a datagram from packets
113 | // with the encode/decode function
114 | // and sets the reliability of the
115 | // encapsulated packet to a custom one
116 | // and the order of the datagram
117 | // to a custom sequence number
118 | func (db *DatagramBuilder) BuildRawFromPackets(packets []packets.IPacket, reliability byte, sequenceNumber, orderIndex, messageIndex uint32) protocol.Datagram {
119 | batch := NewMinecraftPacketBatch()
120 | for _, p := range packets {
121 | batch.AddPacket(p)
122 | }
123 | batch.Encode()
124 | encapsulated := protocol.NewEncapsulatedPacket()
125 | encapsulated.HasSplit = false
126 | encapsulated.Reliability = reliability
127 | encapsulated.OrderIndex = orderIndex
128 | encapsulated.MessageIndex = messageIndex
129 | encapsulated.Buffer = batch.Buffer
130 | datagram := protocol.NewDatagram()
131 | datagram.SequenceNumber = sequenceNumber
132 | datagram.AddPacket(encapsulated)
133 | datagram.Encode()
134 | return *datagram
135 | }
--------------------------------------------------------------------------------
/default_handlers.go:
--------------------------------------------------------------------------------
1 | package goproxy
2 |
3 | import (
4 | "github.com/infinitygamers/goproxy/info"
5 | "github.com/infinitygamers/goproxy/packets"
6 | )
7 |
8 | func RegisterDefaultHandlers(pkHandler *PacketHandler) {
9 | pkHandler.RegisterHandler(info.MovePlayerPacket, func(bytes []byte, host Host, connection *Connection) bool {
10 | move := packets.NewMovePlayerPacket()
11 | move.Buffer = bytes
12 | move.DecodeHeader()
13 | move.Decode()
14 |
15 | if host.IsServer() {
16 | connection.Client.Position = move.Position
17 | }
18 |
19 | return false
20 | })
21 | }
--------------------------------------------------------------------------------
/host.go:
--------------------------------------------------------------------------------
1 | package goproxy
2 |
3 | import (
4 | "net"
5 | "github.com/Irmine/GoMine/net/packets"
6 | )
7 |
8 | type Host interface {
9 | WritePacket(buffer []byte)
10 | SendPacket(packets.IPacket)
11 | SendBatchPacket([]packets.IPacket)
12 | GetAddress() net.UDPAddr
13 | IsClient() bool
14 | IsServer() bool
15 | }
--------------------------------------------------------------------------------
/info/info.go:
--------------------------------------------------------------------------------
1 | package info
2 |
3 |
4 | const (
5 | LoginPacket = 0x01
6 | PlayStatusPacket = 0x02
7 | ServerHandshakePacket = 0x03
8 | ClientHandshakePacket = 0x04
9 | DisconnectPacket = 0x05
10 | ResourcePackInfoPacket = 0x06
11 | ResourcePackStackPacket = 0x07
12 | ResourcePackClientResponsePacket= 0x08
13 | TextPacket = 0x09
14 | SetTimePacket = 0x0a
15 | StartGamePacket = 0x0b
16 | AddPlayerPacket = 0x0c
17 | AddEntityPacket = 0x0d
18 | RemoveEntityPacket = 0x0e
19 | AddItemEntityPacket = 0x0f
20 | AddHangingEntityPacket = 0x10
21 | TakeItemEntityPacket = 0x11
22 | MoveEntityPacket = 0x12
23 | MovePlayerPacket = 0x13
24 | RiderJumpPacket = 0x14
25 | UpdateBlockPacket = 0x15
26 | AddPaintingPacket = 0x16
27 | ExplodePacket = 0x17
28 | LevelSoundEventPacket = 0x18
29 | LevelEventPacket = 0x19
30 | BlockEventPacket = 0x1a
31 | EntityEventPacket = 0x1b
32 | MobEffectPacket = 0x1c
33 | UpdateAttributesPacket = 0x1d
34 | InventoryTransactionPacket = 0x1e
35 | MobEquipmentPacket = 0x1f
36 | MobArmorEquipmentPacket = 0x20
37 | InteractPacket = 0x21
38 | BlockPickRequestPacket = 0x22
39 | EntityPickRequestPacket = 0x23
40 | PlayerActionPacket = 0x24
41 | EntityFallPacket = 0x25
42 | HurtArmorPacket = 0x26
43 | SetEntityDataPacket = 0x27
44 | SetEntityMotionPacket = 0x28
45 | SetEntityLinkPacket = 0x29
46 | SetHealthPacket = 0x2a
47 | SetSpawnPositionPacket = 0x2b
48 | AnimatePacket = 0x2c
49 | RespawnPacket = 0x2d
50 | ContainerOpenPacket = 0x2e
51 | ContainerClosePacket = 0x2f
52 | PlayerHotbarPacket = 0x30
53 | InventoryContentPacket = 0x31
54 | InventorySlotPacket = 0x32
55 | ContainerSetDataPacket = 0x33
56 | CraftingDataPacket = 0x34
57 | CraftingEventPacket = 0x35
58 | GuiDataPickItemPacket = 0x36
59 | AdventureSettingsPacket = 0x37
60 | BlockEntityDataPacket = 0x38
61 | PlayerInputPacket = 0x39
62 | FullChunkDataPacket = 0x3a
63 | SetCommandsEnabledPacket = 0x3b
64 | SetDifficultyPacket = 0x3c
65 | ChangeDimensionPacket = 0x3d
66 | SetPlayerGameTypePacket = 0x3e
67 | PlayerListPacket = 0x3f
68 | SimpleEventPacket = 0x40
69 | EventPacket = 0x41
70 | SpawnExperienceOrbPacket = 0x42
71 | ClientboundMapItemDataPacket = 0x43
72 | MapInfoRequestPacket = 0x44
73 | RequestChunkRadiusPacket = 0x45
74 | ChunkRadiusUpdatedPacket = 0x46
75 | ItemFrameDropItemPacket = 0x47
76 | GameRulesChangedPacket = 0x48
77 | CameraPacket = 0x49
78 | BossEventPacket = 0x4a
79 | ShowCreditsPacket = 0x4b
80 | AvailableCommandsPacket = 0x4c
81 | CommandRequestPacket = 0x4d
82 | CommandBlockUpdatePacket = 0x4e
83 | CommandOutputPacket = 0x4f
84 | UpdateTradePacket = 0x50
85 | UpdateEquipPacket = 0x51
86 | ResourcePackDataInfoPacket = 0x52
87 | ResourcePackChunkDataPacket = 0x53
88 | ResourcePackChunkRequestPacket = 0x54
89 | TransferPacket = 0x55
90 | PlaySoundPacket = 0x56
91 | StopSoundPacket = 0x57
92 | SetTitlePacket = 0x58
93 | AddBehaviorTreePacket = 0x59
94 | StructureBlockUpdatePacket = 0x5a
95 | ShowStoreOfferPacket = 0x5b
96 | PurchaseReceiptPacket = 0x5c
97 | PlayerSkinPacket = 0x5d
98 | SubClientLoginPacket = 0x5e
99 | WSConnectPacket = 0x5f
100 | SetLastHurtByPacket = 0x60
101 | BookEditPacket = 0x61
102 | NpcRequestPacket = 0x62
103 | PhotoTransferPacket = 0x63
104 | ModalFormRequestPacket = 0x64
105 | ModalFormResponsePacket = 0x65
106 | ServerSettingsRequestPacket = 0x66
107 | ServerSettingsResponsePacket = 0x67
108 | ShowProfilePacket = 0x68
109 | SetDefaultGameTypePacket = 0x69
110 | )
--------------------------------------------------------------------------------
/logger.go:
--------------------------------------------------------------------------------
1 | package goproxy
2 |
3 | import (
4 | "time"
5 | "fmt"
6 | )
7 |
8 | const (
9 | AnsiPre = "\u001b["
10 | AnsiReset = AnsiPre + "0m"
11 |
12 | AnsiBold = AnsiPre + "1m"
13 | AnsiItalic = AnsiPre + "3m"
14 | AnsiUnderlined = AnsiPre + "4m"
15 |
16 | AnsiBlack = AnsiPre + "30m"
17 | AnsiRed = AnsiPre + "31m"
18 | AnsiGreen = AnsiPre + "32m"
19 | AnsiYellow = AnsiPre + "33m"
20 | AnsiBlue = AnsiPre + "34m"
21 | AnsiMagenta = AnsiPre + "35m"
22 | AnsiCyan = AnsiPre + "36m"
23 | AnsiWhite = AnsiPre + "37m"
24 | AnsiGray = AnsiPre + "30;1m"
25 |
26 | AnsiBrightRed = AnsiPre + "31;1m"
27 | AnsiBrightGreen = AnsiPre + "32;1m"
28 | AnsiBrightYellow = AnsiPre + "33;1m"
29 | AnsiBrightBlue = AnsiPre + "34;1m"
30 | AnsiBrightMagenta = AnsiPre + "35;1m"
31 | AnsiBrightCyan = AnsiPre + "36;1m"
32 | AnsiBrightWhite = AnsiPre + "37;1m"
33 | )
34 |
35 | const (
36 | Pre = "§"
37 |
38 | Black = Pre + "0"
39 | Blue = Pre + "1"
40 | Green = Pre + "2"
41 | Cyan = Pre + "3"
42 | Red = Pre + "4"
43 | Magenta = Pre + "5"
44 | Orange = Pre + "6"
45 | BrightGray = Pre + "7"
46 | Gray = Pre + "8"
47 | BrightBlue = Pre + "9"
48 |
49 | BrightGreen = Pre + "a"
50 | BrightCyan = Pre + "b"
51 | BrightRed = Pre + "c"
52 | BrightMagenta = Pre + "d"
53 | Yellow = Pre + "e"
54 | White = Pre + "f"
55 |
56 | Obfuscated = Pre + "k"
57 | Bold = Pre + "l"
58 | StrikeThrough = Pre + "m"
59 | Underlined = Pre + "n"
60 | Italic = Pre + "o"
61 |
62 | Reset = Pre + "r"
63 | )
64 |
65 | const (
66 | InfoPrefix = "INFO"
67 | AlertPrefix = "ALERT"
68 | NoticePrefix = "NOTICE"
69 | DebugPrefix = "DEBUG"
70 | PanicPrefix = "PANIC"
71 | )
72 |
73 | // returns a log prefix with custom prefix
74 | func LogFormat(prefix string) string {
75 | now := time.Now()
76 | return "[" + now.Format("2006-01-02 15:04:05") + "][Log/" + prefix + "]: "
77 | }
78 |
79 | func Info(log ...interface{}) {
80 | fmt.Print(AnsiYellow, LogFormat(InfoPrefix), AnsiWhite)
81 | fmt.Println(log...)
82 | }
83 |
84 | func Alert(log ...interface{}) {
85 | fmt.Print(AnsiRed, LogFormat(AlertPrefix), AnsiYellow)
86 | fmt.Println(log...)
87 | }
88 |
89 | func Notice(log ...interface{}) {
90 | fmt.Print(AnsiCyan, LogFormat(NoticePrefix), AnsiWhite)
91 | fmt.Println(log...)
92 | }
93 |
94 | func Debug(log ...interface{}) {
95 | fmt.Print(AnsiWhite, LogFormat(DebugPrefix), AnsiWhite)
96 | fmt.Println(log...)
97 | }
98 |
99 | func Panic(log ...interface{}) {
100 | fmt.Print(AnsiBold, AnsiRed, LogFormat(PanicPrefix))
101 | fmt.Println(log...)
102 | }
--------------------------------------------------------------------------------
/minecraft_batch_packet.go:
--------------------------------------------------------------------------------
1 | package goproxy
2 |
3 | import (
4 | "github.com/irmine/binutils"
5 | "github.com/Irmine/GoMine/net/packets"
6 | "bytes"
7 | "compress/zlib"
8 | "io/ioutil"
9 | )
10 |
11 | const (
12 | BatchId = 0xFE
13 | )
14 |
15 | type MinecraftPacketBatch struct {
16 | *binutils.Stream
17 | rawPackets [][]byte
18 | }
19 |
20 | func NewMinecraftPacketBatch() *MinecraftPacketBatch {
21 | var batch = &MinecraftPacketBatch{}
22 | batch.Stream = binutils.NewStream()
23 | return batch
24 | }
25 |
26 | func (batch *MinecraftPacketBatch) AddPacket(packet packets.IPacket) {
27 | packet.EncodeHeader()
28 | packet.Encode()
29 | batch.AddRawPacket(packet.GetBuffer())
30 | }
31 |
32 | func (batch *MinecraftPacketBatch) AddRawPacket(packet []byte) {
33 | batch.rawPackets = append(batch.rawPackets, packet)
34 | }
35 |
36 | func (batch *MinecraftPacketBatch) GetRawPackets() [][]byte {
37 | return batch.rawPackets
38 | }
39 |
40 | func (batch *MinecraftPacketBatch) Encode() {
41 | batch.ResetStream()
42 | batch.PutByte(BatchId)
43 |
44 | stream := binutils.NewStream()
45 | for _, p := range batch.rawPackets {
46 | stream.PutLengthPrefixedBytes(p)
47 | }
48 |
49 | // zlib compression
50 | buffer := bytes.Buffer{}
51 | writer := zlib.NewWriter(&buffer)
52 | writer.Write(stream.Buffer)
53 | writer.Close()
54 |
55 | batch.PutBytes(buffer.Bytes())
56 | }
57 |
58 | func (batch *MinecraftPacketBatch) Decode() {
59 | defer func() {
60 | if err := recover(); err != nil {
61 | Alert(err)
62 | }
63 | }()
64 |
65 | batchId := batch.GetByte()
66 |
67 | if batchId != BatchId {
68 | Notice("Packet received is not batch:", batchId)
69 | return
70 | }
71 |
72 | data := batch.Buffer[batch.Offset:]
73 |
74 | reader := bytes.NewReader(data)
75 | zlibReader, err := zlib.NewReader(reader)
76 |
77 | if err != nil {
78 | Alert("Zlib Reader Error:", err)
79 | return
80 | }
81 |
82 | if zlibReader == nil {
83 | Alert("Error while reading from zlib")
84 | return
85 | }
86 |
87 | zlibReader.Close()
88 |
89 | data, err = ioutil.ReadAll(zlibReader)
90 |
91 | if err != nil {
92 | Alert("ioutil Error:", err)
93 | return
94 | }
95 |
96 | batch.ResetStream()
97 | batch.SetBuffer(data)
98 |
99 | for !batch.Feof() {
100 | batch.rawPackets = append(batch.rawPackets, batch.GetLengthPrefixedBytes())
101 | }
102 | }
--------------------------------------------------------------------------------
/packet_handler.go:
--------------------------------------------------------------------------------
1 | package goproxy
2 |
3 | import (
4 | "net"
5 | "github.com/Irmine/GoRakLib/protocol"
6 | "github.com/Irmine/GoMine/net/packets"
7 | )
8 |
9 | const (
10 | ClientHandshakeId = 0x13
11 | ClientCancelConnectId = 0x15
12 | )
13 |
14 | // Indexes is used for the collection of indexes related to datagrams and encapsulated packets.
15 | // It uses several maps and is therefore protected by a mutex.
16 | type Indexes struct {
17 | splits map[int16][]*protocol.EncapsulatedPacket
18 | splitCounts map[int16]uint
19 | splitId int16
20 | }
21 |
22 | // Orders is used to re-order the indexes of encapsulated packets
23 | // this is to avoid message order conflicts with the Client and Server
24 | type Orders struct {
25 | //SplitIndex uint
26 |
27 | // the last encapsulated order
28 | // index number from both hosts
29 | ///OrderIndex uint32
30 |
31 | // the last encapsulated
32 | // message index number from both hosts
33 | //MessageIndex uint32
34 |
35 | // the last datagram sequence
36 | // number from both hosts
37 | SequenceNumber uint32
38 | }
39 |
40 | // PacketHandler handles each datagram and
41 | // calls all registered packet handlers to handle the packet,
42 | // once ready, sends it to the right host
43 | type PacketHandler struct {
44 | // Connection is the Connection between the
45 | // Server and the Client
46 | Conn *Connection
47 | // a map where handler functions are stored
48 | // parameters:
49 | // 1. the bytes received from the packet
50 | // 2. the host to where the packet is headed
51 | // 3. the Connection between the Server and Client
52 | // return true if the packet should be cancelled
53 | handlers map[byte][]func([]byte, Host, *Connection) bool
54 | // used for the collection of indexes
55 | // related to datagrams and encapsulated packets.
56 | splits Indexes
57 | // Orders is used to re-order
58 | // the indexes of encapsulated packets
59 | // this is to avoid message order
60 | // conflicts with the Client and Server
61 | orders Orders
62 | // DatagramBuilds builds datagram
63 | // either from a packet or from raw bytes
64 | // datagrams are the communication method
65 | // for the RakNet protocol
66 | DatagramBuilder DatagramBuilder
67 | // the number of the last datagram
68 | // sent by both hosts
69 | lastSequenceNumber uint32
70 | // the last datagram received from both hosts
71 | datagram *protocol.Datagram
72 | // a slice of raw packets that will be
73 | // sent out to the client next tick, packets are sent
74 | // every tick via the packet handler,
75 | // 20 ticks = 1 second, 1 tick ~ 0.05 seconds
76 | OutBoundPacketsClient [][]byte
77 | // a slice of raw packets that will be
78 | // sent out to the server next tick, packets are sent
79 | // every tick via the packet handler,
80 | // 20 ticks = 1 second, 1 tick ~ 0.05 seconds
81 | OutBoundPacketsServer [][]byte
82 | // a bool that returns true if the
83 | // Client is ready for packets
84 | Ready bool
85 | }
86 |
87 | // returns a new packet handler
88 | // PacketHandler handles each datagram and
89 | // calls all registered packet handlers to handle the packet,
90 | // once ready, sends it to the right host
91 | func NewPacketHandler() *PacketHandler {
92 | h := PacketHandler{}
93 | h.handlers = make(map[byte][]func([]byte, Host, *Connection) bool)
94 | h.splits = Indexes{splits: make(map[int16][]*protocol.EncapsulatedPacket), splitCounts: make(map[int16]uint)}
95 | h.DatagramBuilder = NewDatagramBuilder()
96 | h.DatagramBuilder.pkHandler = &h
97 | h.OutBoundPacketsClient = [][]byte{}
98 | h.OutBoundPacketsServer = [][]byte{}
99 | h.orders = Orders{}
100 | return &h
101 | }
102 |
103 | // registers a packet handler with a certain packet id
104 | // every function should have these parameters:
105 | // 1. the bytes received from the packet
106 | // 2. the host to where the packet is headed
107 | // 3. the Connection between the Server and Client
108 | // return true if the packet should be cancelled
109 | func (pkHandler *PacketHandler) RegisterHandler(pkId byte, f func([]byte, Host, *Connection) bool) {
110 | if _, ok := pkHandler.handlers[pkId]; !ok {
111 | pkHandler.handlers[pkId] = []func([]byte, Host, *Connection) bool {}
112 | }
113 | pkHandler.handlers[pkId] = append(pkHandler.handlers[pkId], f)
114 | }
115 |
116 | // calls packet handlers for a certain packet id
117 | // returns true if some handler cancelled the packet
118 | func (pkHandler *PacketHandler) CallPacketHandlers(pkId byte, host Host, packet []byte) bool {
119 | cancelled := false
120 | if _, ok := pkHandler.handlers[pkId]; ok {
121 | for _, v := range pkHandler.handlers[pkId] {
122 | if v(packet, host, pkHandler.Conn) {
123 | cancelled = true
124 | }
125 | }
126 | }
127 | return cancelled //return true if packet is cancelled
128 | }
129 |
130 | // Sends the last datagram received from one host
131 | // to the other host
132 | func (pkHandler *PacketHandler) FlowDatagram(host Host) {
133 | datagram := pkHandler.datagram
134 | datagram.Encode()
135 | host.WritePacket(datagram.Buffer)
136 | }
137 |
138 | // adds a packet to the slice of
139 | // packets that will be sent out to the client next tick,
140 | // packets are sent every tick via the packet handler,
141 | // 20 ticks = 1 second, 1 tick ~ 0.05 seconds
142 | func (pkHandler *PacketHandler) AddOutboundPacketClient(packet packets.IPacket) {
143 | packet.EncodeHeader()
144 | packet.Encode()
145 | pkHandler.OutBoundPacketsClient = append(pkHandler.OutBoundPacketsClient, packet.GetBuffer())
146 | }
147 |
148 | // adds a raw packet to the slice of
149 | // packets that will be sent out to the client next tick,
150 | // packets are sent every tick via the packet handler,
151 | // 20 ticks = 1 second, 1 tick ~ 0.05 seconds
152 | func (pkHandler *PacketHandler) AddOutboundRawPacketClient(packet []byte) {
153 | pkHandler.OutBoundPacketsClient = append(pkHandler.OutBoundPacketsClient, packet)
154 | }
155 |
156 | // adds a packet to the slice of
157 | // packets that will be sent out to the server next tick,
158 | // packets are sent every tick via the packet handler,
159 | // 20 ticks = 1 second, 1 tick ~ 0.05 seconds
160 | func (pkHandler *PacketHandler) AddOutboundPacketServer(packet packets.IPacket) {
161 | packet.EncodeHeader()
162 | packet.Encode()
163 | pkHandler.OutBoundPacketsServer = append(pkHandler.OutBoundPacketsServer, packet.GetBuffer())
164 | }
165 |
166 | // adds a raw packet to the slice of
167 | // packets that will be sent out to the server next tick,
168 | // packets are sent every tick via the packet handler,
169 | // 20 ticks = 1 second, 1 tick ~ 0.05 seconds
170 | func (pkHandler *PacketHandler) AddOutboundRawPacketServer(packet []byte) {
171 | pkHandler.OutBoundPacketsServer = append(pkHandler.OutBoundPacketsServer, packet)
172 | }
173 |
174 | // handles encapsulated packet
175 | // if the packet is batch it will call the packet handlers
176 | // if not it will just continue on sending the datagram
177 | func (pkHandler *PacketHandler) HandleEncapsulated(packet *protocol.EncapsulatedPacket, host Host, addr net.UDPAddr) bool {
178 | handled := false
179 | PkId := packet.Buffer[0]
180 | if PkId == BatchId {
181 | if pkHandler.Ready {
182 | batch := NewMinecraftPacketBatch()
183 | batch.SetBuffer(packet.Buffer)
184 | batch.Decode()
185 | batch2 := NewMinecraftPacketBatch()
186 |
187 | for _, pk := range batch.GetRawPackets() {
188 | pkId := pk[0]
189 | if !pkHandler.CallPacketHandlers(pkId, host, pk) {
190 | batch2.AddRawPacket(pk)
191 | }
192 | }
193 |
194 | if host.IsServer() {
195 | if toServer := pkHandler.OutBoundPacketsServer; len(toServer) > 0 {
196 | for _, pk := range toServer {
197 | batch2.AddRawPacket(pk)
198 | }
199 | pkHandler.OutBoundPacketsServer = nil
200 | }
201 | }else{
202 | if toClient := pkHandler.OutBoundPacketsClient; len(toClient) > 0 {
203 | for _, pk := range toClient {
204 | batch2.AddRawPacket(pk)
205 | }
206 | pkHandler.OutBoundPacketsClient = nil
207 | }
208 | }
209 |
210 | batch2.Encode()
211 | encap := protocol.NewEncapsulatedPacket()
212 | encap.Buffer = batch2.Buffer
213 | encap.Reliability = packet.Reliability
214 | encap.HasSplit = false
215 | encap.Length = packet.Length
216 | encap.MessageIndex = packet.MessageIndex
217 | encap.OrderIndex = packet.OrderIndex
218 | dgram := protocol.NewDatagram()
219 | dgram.AddPacket(encap)
220 | dgram.SequenceNumber = pkHandler.lastSequenceNumber
221 | dgram.Encode()
222 |
223 | host.WritePacket(dgram.Buffer)
224 |
225 | handled = true
226 | }
227 |
228 | }else if PkId == ClientHandshakeId {
229 | Info(AnsiGreen + "Client has connected to the Server.")
230 | pkHandler.FlowDatagram(host)
231 | pkHandler.Conn.Client.SendJoinMessage()
232 | pkHandler.Ready = true
233 | handled = true
234 | } else if PkId == ClientCancelConnectId {
235 | Info(AnsiBrightRed + "Client has disconnected from the Server.")
236 | pkHandler.Conn.Client.SetConnected(false)
237 | pkHandler.FlowDatagram(host)
238 | pkHandler.Ready = false
239 | handled = true
240 | } else {
241 |
242 | switch PkId {
243 | case protocol.IdConnectionRequest:
244 | Info(AnsiBrightCyan + "Connection request from client")
245 | case protocol.IdConnectionAccept:
246 | Info(AnsiBrightCyan + "Connection request accepted from server")
247 | }
248 |
249 | pkHandler.FlowDatagram(host)
250 | handled = true
251 | }
252 | return handled
253 | }
254 |
255 | // Decodes a split encapsulated packet
256 | // and turns it into one
257 | func (pkHandler *PacketHandler) DecodeSplit(packet *protocol.EncapsulatedPacket) *protocol.EncapsulatedPacket {
258 | id := packet.SplitId
259 |
260 | if pkHandler.splits.splits[id] == nil {
261 | pkHandler.splits.splits[id] = make([]*protocol.EncapsulatedPacket, packet.SplitCount)
262 | pkHandler.splits.splitCounts[id] = 0
263 | }
264 |
265 | if pk := pkHandler.splits.splits[id][packet.SplitIndex]; pk == nil {
266 | pkHandler.splits.splitCounts[id]++
267 | }
268 |
269 | pkHandler.splits.splits[id][packet.SplitIndex] = packet
270 |
271 | if pkHandler.splits.splitCounts[id] == packet.SplitCount {
272 | newPacket := protocol.NewEncapsulatedPacket()
273 | for _, pk := range pkHandler.splits.splits[id] {
274 | newPacket.PutBytes(pk.Buffer)
275 | }
276 |
277 | delete(pkHandler.splits.splits, id)
278 | return newPacket
279 | }
280 |
281 | return nil
282 | }
283 |
284 | // this handles encapsulated packets that
285 | // come in more than one part, construct a single one
286 | // and calls the HandleEncapsulated function
287 | func (pkHandler *PacketHandler) HandleSplitEncapsulated(packet *protocol.EncapsulatedPacket, host Host, addr net.UDPAddr) bool {
288 | d := pkHandler.DecodeSplit(packet)
289 |
290 | if d != nil {
291 | return pkHandler.HandleEncapsulated(d, host, addr)
292 | }
293 |
294 | return false
295 | }
296 |
297 | // this handles all the incoming packets
298 | // after the Client has clicked the Server
299 | // of the Proxy
300 | func (pkHandler *PacketHandler) HandleIncomingPacket(buffer []byte, host Host, addr net.UDPAddr) {
301 | MessageId := buffer[0]
302 | if (MessageId & protocol.BitFlagValid) != 0 {
303 | if (MessageId & protocol.BitFlagIsNak) != 0 {
304 | nak := protocol.NewNAK()
305 | nak.SetBuffer(buffer)
306 | nak.Decode()
307 | nak.Encode()
308 | host.WritePacket(nak.Buffer)
309 | } else if (MessageId & protocol.BitFlagIsAck) != 0 {
310 | ack := protocol.NewACK()
311 | ack.SetBuffer(buffer)
312 | ack.Decode()
313 | ack.Encode()
314 | host.WritePacket(ack.Buffer)
315 | } else {
316 | datagram := protocol.NewDatagram()
317 | datagram.SetBuffer(buffer)
318 | datagram.Decode()
319 |
320 | pkHandler.datagram = datagram
321 | pkHandler.lastSequenceNumber = datagram.SequenceNumber
322 | packets2 := datagram.GetPackets()
323 |
324 | if len(*packets2) != 0 {
325 | for _, pk := range *packets2 {
326 | if pk.HasSplit {
327 | if !pkHandler.HandleSplitEncapsulated(pk, host, addr) {
328 | pkHandler.FlowDatagram(host)
329 | }
330 | } else {
331 | if !pkHandler.HandleEncapsulated(pk, host, addr) {
332 | pkHandler.FlowDatagram(host)
333 | }
334 | }
335 | }
336 | }else{
337 | pkHandler.FlowDatagram(host)
338 | }
339 | }
340 | } else {
341 | host.WritePacket(buffer)
342 | }
343 | }
--------------------------------------------------------------------------------
/packets/add_entity_packet.go:
--------------------------------------------------------------------------------
1 | package packets
2 |
3 | import (
4 | "github.com/golang/geo/r3"
5 | "github.com/Irmine/GoMine/net/packets"
6 | "github.com/irmine/worlds/entities/data"
7 | "github.com/infinitygamers/goproxy/info"
8 | )
9 |
10 | type AddEntityPacket struct {
11 | *packets.Packet
12 | UniqueId int64
13 | RuntimeId uint64
14 | EntityType uint32
15 | Position r3.Vector
16 | Motion r3.Vector
17 | Rotation data.Rotation
18 |
19 | Attributes data.AttributeMap
20 | EntityData map[uint32][]interface{}
21 | }
22 |
23 | func NewAddEntityPacket() *AddEntityPacket {
24 | return &AddEntityPacket{packets.NewPacket(info.AddEntityPacket), 0, 0, 0, r3.Vector{}, r3.Vector{}, data.Rotation{}, data.NewAttributeMap(), nil}
25 | }
26 |
27 | func (pk *AddEntityPacket) Encode() {
28 | pk.PutEntityUniqueId(pk.UniqueId)
29 | pk.PutEntityRuntimeId(pk.RuntimeId)
30 | pk.PutUnsignedVarInt(pk.EntityType)
31 | pk.PutVector(pk.Position)
32 | pk.PutVector(pk.Motion)
33 | pk.PutEntityRotation(pk.Rotation)
34 | pk.PutAttributeMap(pk.Attributes)
35 | pk.PutEntityData(pk.EntityData)
36 | pk.PutUnsignedVarInt(0)
37 | }
38 |
39 | func (pk *AddEntityPacket) Decode() {
40 | pk.UniqueId = pk.GetEntityUniqueId()
41 | pk.RuntimeId = pk.GetEntityRuntimeId()
42 | pk.EntityType = pk.GetUnsignedVarInt()
43 | pk.Position = pk.GetVector()
44 | pk.Motion = pk.GetVector()
45 | pk.Rotation = pk.GetEntityRotation()
46 | pk.Attributes = pk.GetAttributeMap()
47 | pk.EntityData = pk.GetEntityData()
48 | }
49 |
--------------------------------------------------------------------------------
/packets/add_player_packet.go:
--------------------------------------------------------------------------------
1 | package packets
2 |
3 | import (
4 | "github.com/google/uuid"
5 | "github.com/golang/geo/r3"
6 | "github.com/irmine/worlds/entities/data"
7 | "github.com/Irmine/GoMine/net/packets"
8 | "github.com/infinitygamers/goproxy/info"
9 | )
10 |
11 | type AddPlayerPacket struct {
12 | *packets.Packet
13 | UUID uuid.UUID
14 | Username string
15 | DisplayName string
16 | Platform int32
17 | UnknownString string
18 | EntityUniqueId int64
19 | EntityRuntimeId uint64
20 | Position r3.Vector
21 | Motion r3.Vector
22 | Rotation data.Rotation
23 | // HandItem TODO: Items.
24 | Metadata map[uint32][]interface{}
25 | Flags uint32
26 | CommandPermission uint32
27 | Flags2 uint32
28 | PlayerPermission uint32
29 | CustomFlags uint32
30 | Long1 int64
31 | }
32 |
33 | func NewAddPlayerPacket() *AddPlayerPacket {
34 | return &AddPlayerPacket{Packet: packets.NewPacket(info.AddPlayerPacket), Metadata: make(map[uint32][]interface{}), Motion: r3.Vector{}}
35 | }
36 |
37 | func (pk *AddPlayerPacket) Encode() {
38 | pk.PutUUID(pk.UUID)
39 | pk.PutString(pk.Username)
40 | pk.PutString(pk.DisplayName)
41 | pk.PutVarInt(pk.Platform)
42 |
43 | pk.PutEntityUniqueId(pk.EntityUniqueId)
44 | pk.PutEntityRuntimeId(pk.EntityRuntimeId)
45 | pk.PutString(pk.UnknownString)
46 |
47 | pk.PutVector(pk.Position)
48 | pk.PutVector(pk.Motion)
49 | pk.PutPlayerRotation(pk.Rotation)
50 |
51 | pk.PutVarInt(0) // TODO
52 | pk.PutEntityData(pk.Metadata)
53 |
54 | pk.PutUnsignedVarInt(pk.Flags)
55 | pk.PutUnsignedVarInt(pk.CommandPermission)
56 | pk.PutUnsignedVarInt(pk.Flags2)
57 | pk.PutUnsignedVarInt(pk.PlayerPermission)
58 | pk.PutUnsignedVarInt(pk.CustomFlags)
59 |
60 | pk.PutVarLong(pk.Long1)
61 |
62 | pk.PutUnsignedVarInt(0) // TODO
63 | }
64 |
65 | func (pk *AddPlayerPacket) Decode() {
66 | pk.UUID = pk.GetUUID()
67 | pk.Username = pk.GetString()
68 | pk.DisplayName = pk.GetString()
69 | pk.Platform = pk.GetVarInt()
70 |
71 | pk.EntityUniqueId = pk.GetEntityUniqueId()
72 | pk.EntityRuntimeId = pk.GetEntityRuntimeId()
73 | pk.UnknownString = pk.GetString()
74 |
75 | pk.Position = pk.GetVector()
76 | pk.Motion = pk.GetVector()
77 | pk.Rotation = pk.GetPlayerRotation()
78 |
79 | pk.GetVarInt()
80 | pk.Metadata = pk.GetEntityData()
81 |
82 | pk.Flags = pk.GetUnsignedVarInt()
83 | pk.CommandPermission = pk.GetUnsignedVarInt()
84 | pk.Flags2 = pk.GetUnsignedVarInt()
85 | pk.PlayerPermission = pk.GetUnsignedVarInt()
86 | pk.CustomFlags = pk.GetUnsignedVarInt()
87 |
88 | pk.Long1 = pk.GetVarLong()
89 |
90 | pk.GetUnsignedVarInt()
91 | }
92 |
--------------------------------------------------------------------------------
/packets/interact_packet.go:
--------------------------------------------------------------------------------
1 | package packets
2 |
3 | import (
4 | "github.com/Irmine/GoMine/net/packets"
5 | "github.com/infinitygamers/goproxy/info"
6 | )
7 |
8 | const (
9 | RightClick = 1
10 | LeftClick = 2
11 | LeaveCehicle = 3
12 | MouseOver = 4
13 | )
14 |
15 | type InteractPacket struct {
16 | *packets.Packet
17 | Action byte
18 | RuntimeId uint64
19 | }
20 |
21 | func NewInteractPacket() *InteractPacket {
22 | return &InteractPacket{ packets.NewPacket(info.SetPlayerGameTypePacket), 0, 0}
23 | }
24 |
25 | func (pk *InteractPacket) Encode() {
26 | pk.PutByte(pk.Action)
27 | pk.PutUnsignedVarLong(pk.RuntimeId)
28 | }
29 |
30 | func (pk *InteractPacket) Decode() {
31 | pk.Action = pk.GetByte()
32 | pk.RuntimeId = pk.GetUnsignedVarLong()
33 | }
--------------------------------------------------------------------------------
/packets/inventory_transaction_packet.go:
--------------------------------------------------------------------------------
1 | package packets
2 |
3 | import (
4 | "github.com/golang/geo/r3"
5 | "github.com/irmine/gomine/net/info"
6 | "github.com/Irmine/GoMine/net/packets"
7 | "github.com/infinitygamers/goproxy/packets/inventoryio"
8 | "github.com/infinitygamers/goproxy/packets/inventoryio/stream"
9 | )
10 |
11 | /**
12 | * Transaction Types
13 | */
14 | const (
15 | Normal = iota + 0
16 | Mismatch
17 | UseItem
18 | UseItemOnEntity
19 | ReleaseItem
20 | )
21 |
22 | // Action Types
23 | const (
24 | ItemClickBlock = iota + 0
25 | ItemClickAir
26 | ItemBreakBlock
27 |
28 | //CONSUMABLE ITEMS
29 | ItemRelease = iota + 0
30 | ItemConsume
31 | )
32 |
33 | // Entity Action ztypes
34 | const (
35 | ItemOnEntityInteract = iota + 0
36 | ItemOnEntityAttack
37 | )
38 |
39 | type InventoryTransactionPacket struct {
40 | *packets.Packet
41 | InvStream *stream.InventoryActionStream
42 | ActionList *inventoryio.InventoryActionIOList
43 | TransactionType, ActionType uint32
44 | Face, HotbarSlot int32
45 | ItemSlot *stream.VirtualItem
46 | BlockX int32
47 | BlockY uint32
48 | BlockZ int32
49 | PlayerPosition, ClickPosition, HeadPosition r3.Vector
50 | RuntimeId uint64
51 | }
52 |
53 | func NewInventoryTransactionPacket() *InventoryTransactionPacket {
54 | pk := &InventoryTransactionPacket{Packet: packets.NewPacket(info.PacketIds200[info.InventoryTransactionPacket]),
55 | ActionList: inventoryio.NewInventoryActionIOList(),
56 | TransactionType: 0,
57 | ActionType: 0,
58 | Face: 0,
59 | HotbarSlot: 0,
60 | ItemSlot: &stream.VirtualItem{},
61 | PlayerPosition: r3.Vector{},
62 | ClickPosition: r3.Vector{},
63 | HeadPosition: r3.Vector{},
64 | RuntimeId: 0,
65 | }
66 | pk.InvStream = stream.NewInventoryActionStream(pk.Stream)
67 | return pk
68 | }
69 |
70 |
71 | func (pk *InventoryTransactionPacket) GetBlockPos() {
72 | pk.BlockX = pk.GetVarInt()
73 | pk.BlockY = pk.GetUnsignedVarInt()
74 | pk.BlockZ = pk.GetVarInt()
75 | }
76 |
77 | func (pk *InventoryTransactionPacket) PutBlockPos() {
78 | pk.PutVarInt(pk.BlockX)
79 | pk.PutUnsignedVarInt(pk.BlockY)
80 | pk.PutVarInt(pk.BlockZ)
81 | }
82 |
83 | func (pk *InventoryTransactionPacket) Encode() {
84 | pk.PutUnsignedVarInt(pk.TransactionType)
85 | pk.ActionList.WriteToBuffer(pk.InvStream)
86 |
87 | switch pk.TransactionType {
88 | case Normal, Mismatch:
89 | break
90 | case UseItem:
91 | pk.PutUnsignedVarInt(pk.ActionType)
92 | pk.PutBlockPos()
93 | pk.PutVarInt(pk.Face)
94 | pk.PutVarInt(pk.HotbarSlot)
95 | pk.InvStream.PutVirtualItem(pk.ItemSlot)
96 | pk.PutVector(pk.PlayerPosition)
97 | pk.PutVector(pk.ClickPosition)
98 | break
99 | case UseItemOnEntity:
100 | pk.PutUnsignedVarLong(pk.RuntimeId)
101 | pk.PutUnsignedVarInt(pk.ActionType)
102 | pk.PutVarInt(pk.HotbarSlot)
103 | pk.InvStream.PutVirtualItem(pk.ItemSlot)
104 | pk.PutVector(pk.PlayerPosition)
105 | pk.PutVector(pk.ClickPosition)
106 | break
107 | case ReleaseItem:
108 | pk.PutUnsignedVarInt(pk.ActionType)
109 | pk.PutVarInt(pk.HotbarSlot)
110 | pk.InvStream.PutVirtualItem(pk.ItemSlot)
111 | pk.PutVector(pk.HeadPosition)
112 | break
113 | default:
114 | panic("Unknown transaction type passed: " + string(pk.TransactionType))
115 | }
116 | }
117 |
118 | func (pk *InventoryTransactionPacket) Decode() {
119 | pk.TransactionType = pk.GetUnsignedVarInt()
120 |
121 | pk.ActionList.ReadFromBuffer(pk.InvStream)
122 |
123 | switch pk.TransactionType{
124 | case Normal, Mismatch:
125 | break
126 | case UseItem:
127 | pk.ActionType = pk.GetUnsignedVarInt()
128 | pk.GetBlockPos()
129 | pk.Face = pk.GetVarInt()
130 | pk.HotbarSlot = pk.GetVarInt()
131 | pk.ItemSlot = pk.InvStream.GetVirtualItem()
132 | pk.PlayerPosition = pk.GetVector()
133 | pk.ClickPosition = pk.GetVector()
134 | case UseItemOnEntity:
135 | pk.RuntimeId = pk.GetUnsignedVarLong()
136 | pk.ActionType = pk.GetUnsignedVarInt()
137 | pk.HotbarSlot = pk.GetVarInt()
138 | pk.ItemSlot = pk.InvStream.GetVirtualItem()
139 | pk.PlayerPosition = pk.GetVector()
140 | pk.ClickPosition = pk.GetVector()
141 | case ReleaseItem:
142 | pk.ActionType = pk.GetUnsignedVarInt()
143 | pk.HotbarSlot = pk.GetVarInt()
144 | pk.ItemSlot = pk.InvStream.GetVirtualItem()
145 | pk.HeadPosition = pk.GetVector()
146 | default:
147 | panic("Error: Unknown transaction type received: " + string(pk.TransactionType))
148 | }
149 | }
150 |
--------------------------------------------------------------------------------
/packets/inventoryio/inventory_action_io.go:
--------------------------------------------------------------------------------
1 | package inventoryio
2 |
3 | import (
4 | "github.com/infinitygamers/goproxy/packets/inventoryio/stream"
5 | )
6 |
7 | const (
8 | ContainerSource = iota + 0
9 | WorldSource = 2
10 | //CreativeSource = 3
11 | )
12 |
13 | type InventoryActionIO struct {
14 | Source uint32
15 | WindowId int32
16 | SourceFlags uint32
17 | InventorySlot uint32
18 | OldItem *stream.VirtualItem
19 | NewItem *stream.VirtualItem
20 | }
21 |
22 | func NewInventoryActionIO() InventoryActionIO{
23 | return InventoryActionIO{}
24 | }
25 |
26 | func (IO *InventoryActionIO) WriteToBuffer(bs *stream.InventoryActionStream) {
27 | bs.PutUnsignedVarInt(IO.Source)
28 |
29 | switch IO.Source {
30 | case ContainerSource:
31 | bs.PutVarInt(IO.WindowId)
32 | break
33 | case WorldSource:
34 | bs.PutUnsignedVarInt(IO.SourceFlags)
35 | break
36 | }
37 |
38 | bs.PutUnsignedVarInt(IO.InventorySlot)
39 | bs.PutVirtualItem(IO.OldItem)
40 | bs.PutVirtualItem(IO.NewItem)
41 | }
42 |
43 | func (IO *InventoryActionIO) ReadFromBuffer(bs *stream.InventoryActionStream) InventoryActionIO {
44 | v := NewInventoryActionIO()
45 | v.Source = bs.GetUnsignedVarInt()
46 | switch v.Source {
47 | case ContainerSource:
48 | v.WindowId = bs.GetVarInt()
49 | break
50 | case WorldSource:
51 | v.SourceFlags = bs.GetUnsignedVarInt()
52 | break
53 | }
54 |
55 | IO.InventorySlot = bs.GetUnsignedVarInt()
56 | IO.OldItem = bs.GetVirtualItem()
57 | IO.NewItem = bs.GetVirtualItem()
58 |
59 | return v
60 | }
--------------------------------------------------------------------------------
/packets/inventoryio/inventory_action_io_list.go:
--------------------------------------------------------------------------------
1 | package inventoryio
2 |
3 | import (
4 | "github.com/infinitygamers/goproxy/packets/inventoryio/stream"
5 | )
6 |
7 | type InventoryActionIOList struct {
8 | List []InventoryActionIO
9 | }
10 |
11 | func NewInventoryActionIOList() *InventoryActionIOList{
12 | return &InventoryActionIOList{}
13 | }
14 |
15 | func (IOList *InventoryActionIOList) GetCount() int {
16 | return len(IOList.List)
17 | }
18 |
19 | func (IOList *InventoryActionIOList) PutAction(io InventoryActionIO) {
20 | IOList.List = append(IOList.List, io)
21 | }
22 |
23 | func (IOList *InventoryActionIOList) WriteToBuffer(bs *stream.InventoryActionStream) {
24 | c := len(IOList.List)
25 | bs.PutUnsignedVarInt(uint32(c))
26 | for i := 0; i < c; i++ {
27 | IOList.List[i].WriteToBuffer(bs)
28 | }
29 | }
30 |
31 | func (IOList *InventoryActionIOList) ReadFromBuffer(bs *stream.InventoryActionStream) *InventoryActionIOList{
32 | c := bs.GetUnsignedVarInt()
33 | for i := uint32(0); i < c; i ++{
34 | a := NewInventoryActionIO()
35 | a.ReadFromBuffer(bs)
36 | IOList.PutAction(a)
37 | }
38 | return IOList
39 | }
--------------------------------------------------------------------------------
/packets/inventoryio/stream/inventory_action_stream.go:
--------------------------------------------------------------------------------
1 | package stream
2 |
3 | import (
4 | "github.com/irmine/binutils"
5 | )
6 |
7 | type VirtualItem struct {
8 | Id int32
9 | Damage int32
10 | Count int32
11 | Nbt string
12 | }
13 |
14 | type InventoryActionStream struct {
15 | *binutils.Stream
16 | }
17 |
18 | func NewInventoryActionStream(stream *binutils.Stream) *InventoryActionStream {
19 | return &InventoryActionStream{stream}
20 | }
21 |
22 | func (pk *InventoryActionStream) PutVirtualItem(item *VirtualItem) {
23 | pk.PutVarInt(item.Id)
24 | pk.PutVarInt(((item.Damage & 0x7fff) << 8) | item.Count)
25 | pk.PutLittleShort(int16(len(item.Nbt)))
26 | pk.PutString(item.Nbt)
27 | pk.PutVarInt(0) //todo
28 | pk.PutVarInt(0) //todo
29 | }
30 |
31 | func (pk *InventoryActionStream) GetVirtualItem() *VirtualItem {
32 | id := pk.GetVarInt()
33 |
34 | if id == 0 {
35 | return &VirtualItem{Id: 0, Damage: 0, Count: 0, Nbt: ""}
36 | }
37 |
38 | aux := pk.GetVarInt()
39 | data := aux >> 8
40 |
41 | if data == 0x7fff {
42 | data = -1
43 | }
44 |
45 | count := aux & 0xff
46 |
47 | nbtLen := pk.GetLittleShort()
48 | nbt := ""
49 | if nbtLen > 0 {
50 | //nbt = string(pk.Get(int(nbtLen))) //todo
51 | }
52 |
53 | return &VirtualItem{Id: id, Damage: data, Count: count, Nbt: nbt}
54 | }
--------------------------------------------------------------------------------
/packets/modal_form_request_packet.go:
--------------------------------------------------------------------------------
1 | package packets
2 |
3 | import (
4 | "github.com/Irmine/GoMine/net/packets"
5 | "github.com/infinitygamers/goproxy/info"
6 | )
7 |
8 | type ModalFormRequestPacket struct {
9 | *packets.Packet
10 | FormId uint32
11 | FormData string
12 | }
13 |
14 | func NewModalFormRequestPacket() *ModalFormRequestPacket {
15 | return &ModalFormRequestPacket{packets.NewPacket(info.ModalFormRequestPacket), 0, ""}
16 | }
17 |
18 | func (pk *ModalFormRequestPacket) Encode() {
19 | pk.PutUnsignedVarInt(pk.FormId)
20 | pk.PutString(pk.FormData)
21 | }
22 |
23 | func (pk *ModalFormRequestPacket) Decode() {
24 | pk.FormId = pk.GetUnsignedVarInt()
25 | pk.FormData = pk.GetString()
26 | }
--------------------------------------------------------------------------------
/packets/modal_form_response_packet.go:
--------------------------------------------------------------------------------
1 | package packets
2 |
3 | import (
4 | "github.com/Irmine/GoMine/net/packets"
5 | "github.com/infinitygamers/goproxy/info"
6 | )
7 |
8 | type ModalFormResponsePacket struct {
9 | *packets.Packet
10 | FormId uint32
11 | FormData string
12 | }
13 |
14 | func NewModalFormResponsePacket() *ModalFormResponsePacket {
15 | return &ModalFormResponsePacket{packets.NewPacket(info.ModalFormResponsePacket), 0, ""}
16 | }
17 |
18 | func (pk *ModalFormResponsePacket) Encode() {
19 | pk.PutUnsignedVarInt(pk.FormId)
20 | pk.PutString(pk.FormData)
21 | }
22 |
23 | func (pk *ModalFormResponsePacket) Decode() {
24 | pk.FormId = pk.GetUnsignedVarInt()
25 | pk.FormData = pk.GetString()
26 | }
--------------------------------------------------------------------------------
/packets/move_entity_packet.go:
--------------------------------------------------------------------------------
1 | package packets
2 |
3 | import (
4 | "github.com/golang/geo/r3"
5 | "github.com/irmine/gomine/net/info"
6 | "github.com/Irmine/GoMine/net/packets"
7 | data2 "github.com/irmine/worlds/entities/data"
8 | )
9 |
10 | type MoveEntityPacket struct {
11 | *packets.Packet
12 | RuntimeId uint64
13 | Position r3.Vector
14 | Rotation data2.Rotation
15 | Mode byte
16 | OnGround bool
17 | Teleported bool
18 | }
19 |
20 | func NewMoveEntityPacket() *MoveEntityPacket {
21 | return &MoveEntityPacket{Packet: packets.NewPacket(info.PacketIds200[info.MoveEntityPacket]), Position: r3.Vector{}, Rotation: data2.Rotation{}}
22 | }
23 |
24 | func (pk *MoveEntityPacket) Encode() {
25 | pk.PutEntityRuntimeId(pk.RuntimeId)
26 | pk.PutVector(pk.Position)
27 | pk.PutEntityRotation(pk.Rotation)
28 | pk.PutByte(pk.Mode)
29 | pk.PutBool(pk.OnGround)
30 | pk.PutBool(pk.Teleported)
31 | }
32 |
33 | func (pk *MoveEntityPacket) Decode() {
34 | pk.RuntimeId = pk.GetEntityRuntimeId()
35 | pk.Position = pk.GetVector()
36 | pk.Rotation = pk.GetEntityRotation()
37 | pk.Mode = pk.GetByte()
38 | pk.OnGround = pk.GetBool()
39 | pk.Teleported = pk.GetBool()
40 | }
41 |
--------------------------------------------------------------------------------
/packets/move_player_packet.go:
--------------------------------------------------------------------------------
1 | package packets
2 |
3 | import (
4 | "github.com/golang/geo/r3"
5 | "github.com/irmine/gomine/net/info"
6 | "github.com/Irmine/GoMine/net/packets"
7 | "github.com/irmine/gomine/net/packets/data"
8 | data2 "github.com/irmine/worlds/entities/data"
9 | )
10 |
11 | type MovePlayerPacket struct {
12 | *packets.Packet
13 | RuntimeId uint64
14 | Position r3.Vector
15 | Rotation data2.Rotation
16 | Mode byte
17 | OnGround bool
18 | RidingRuntimeId uint64
19 | ExtraInt1, ExtraInt2 int32
20 | }
21 |
22 | func NewMovePlayerPacket() *MovePlayerPacket {
23 | return &MovePlayerPacket{Packet: packets.NewPacket(info.PacketIds200[info.MovePlayerPacket]), Position: r3.Vector{}, Rotation: data2.Rotation{}}
24 | }
25 |
26 | func (pk *MovePlayerPacket) Encode() {
27 | pk.PutEntityRuntimeId(pk.RuntimeId)
28 | pk.PutVector(pk.Position)
29 | pk.PutPlayerRotation(pk.Rotation)
30 | pk.PutByte(pk.Mode)
31 | pk.PutBool(pk.OnGround)
32 | pk.PutEntityRuntimeId(pk.RidingRuntimeId)
33 | if pk.Mode == data.MoveTeleport {
34 | pk.PutLittleInt(pk.ExtraInt1)
35 | pk.PutLittleInt(pk.ExtraInt2)
36 | }
37 | }
38 |
39 | func (pk *MovePlayerPacket) Decode() {
40 | pk.RuntimeId = pk.GetEntityRuntimeId()
41 | pk.Position = pk.GetVector()
42 | pk.Rotation = pk.GetPlayerRotation()
43 | pk.Mode = pk.GetByte()
44 | pk.OnGround = pk.GetBool()
45 | pk.RidingRuntimeId = pk.GetEntityRuntimeId()
46 | if pk.Mode == data.MoveTeleport {
47 | pk.ExtraInt1 = pk.GetLittleInt()
48 | pk.ExtraInt2 = pk.GetLittleInt()
49 | }
50 | }
51 |
--------------------------------------------------------------------------------
/packets/remove_entity_packet.go:
--------------------------------------------------------------------------------
1 | package packets
2 |
3 | import (
4 | "github.com/Irmine/GoMine/net/packets"
5 | "github.com/infinitygamers/goproxy/info"
6 | )
7 |
8 | type RemoveEntityPacket struct {
9 | *packets.Packet
10 | RuntimeId uint64
11 | }
12 |
13 | func NewRemoveEntityPacket() *RemoveEntityPacket {
14 | return &RemoveEntityPacket{packets.NewPacket(info.RemoveEntityPacket), 0}
15 | }
16 |
17 | func (pk *RemoveEntityPacket) Encode() {
18 | pk.PutEntityRuntimeId(pk.RuntimeId)
19 | }
20 |
21 | func (pk *RemoveEntityPacket) Decode() {
22 | pk.RuntimeId = pk.GetEntityRuntimeId()
23 | }
24 |
--------------------------------------------------------------------------------
/packets/set_game_mode_packet.go:
--------------------------------------------------------------------------------
1 | package packets
2 |
3 | import (
4 | "github.com/Irmine/GoMine/net/packets"
5 | "github.com/infinitygamers/goproxy/info"
6 | )
7 |
8 | type SetGameModePacket struct {
9 | *packets.Packet
10 | GameMode int32
11 | }
12 |
13 | func NewSetGamemodePacket() *SetGameModePacket {
14 | return &SetGameModePacket{ packets.NewPacket(info.SetPlayerGameTypePacket), 0}
15 | }
16 |
17 | func (pk *SetGameModePacket) Encode() {
18 | pk.PutVarInt(pk.GameMode)
19 | }
20 |
21 | func (pk *SetGameModePacket) Decode() {
22 | pk.GameMode = pk.GetVarInt()
23 | }
--------------------------------------------------------------------------------
/packets/set_title_packet.go:
--------------------------------------------------------------------------------
1 | package packets
2 |
3 | import (
4 | "github.com/Irmine/GoMine/net/packets"
5 | "github.com/infinitygamers/goproxy/info"
6 | )
7 |
8 | const (
9 | ClearTitle = iota
10 | ResetTitle
11 | SetTitle
12 | SetSubtitle
13 | SetActionBarMessage
14 | SetAnimationTimes
15 | )
16 |
17 | type SetTitlePacket struct {
18 | *packets.Packet
19 | TitleType int32
20 | Text string
21 | FadeInTime int32
22 | StayTime int32
23 | FadeOutTime int32
24 | }
25 |
26 | func NewSetTitlePacket() *SetTitlePacket {
27 | return &SetTitlePacket{
28 | packets.NewPacket(info.SetTitlePacket),
29 | 0,
30 | "",
31 | 0,
32 | 0,
33 | 0,
34 | }
35 | }
36 |
37 | func (pk *SetTitlePacket) Encode() {
38 | pk.PutVarInt(pk.TitleType)
39 | pk.PutString(pk.Text)
40 | pk.PutVarInt(pk.FadeInTime)
41 | pk.PutVarInt(pk.StayTime)
42 | pk.PutVarInt(pk.FadeOutTime)
43 | }
44 |
45 | func (pk *SetTitlePacket) Decode() {
46 | pk.TitleType = pk.GetVarInt()
47 | pk.Text = pk.GetString()
48 | pk.FadeInTime = pk.GetVarInt()
49 | pk.StayTime = pk.GetVarInt()
50 | pk.FadeOutTime = pk.GetVarInt()
51 | }
--------------------------------------------------------------------------------
/packets/text_packet.go:
--------------------------------------------------------------------------------
1 | package packets
2 |
3 | import (
4 | "github.com/Irmine/GoMine/net/packets"
5 | "github.com/infinitygamers/goproxy/info"
6 | )
7 |
8 | const (
9 | Raw = 0x00
10 | Chat = 0x01
11 | Translation = 0x02
12 | Popup = 0x03
13 | JukeboxPopup = 0x04
14 | Tip = 0x05
15 | System = 0x06
16 | Whisper = 0x07
17 | Announcement = 0x08
18 | )
19 |
20 | type TextPacket struct {
21 | *packets.Packet
22 | TextType byte
23 | Translation bool
24 | Source string
25 | SourceThirdParty string
26 | SourcePlatform int32
27 | Message string
28 | Xuid string
29 | PlatformChatId string
30 |
31 | Params []string
32 | }
33 |
34 | func NewTextPacket() *TextPacket {
35 | return &TextPacket{
36 | packets.NewPacket(info.TextPacket),
37 | Raw,
38 | false,
39 | "",
40 | "",
41 | 0,
42 | "",
43 | "",
44 | "",
45 | []string{},
46 | }
47 | }
48 |
49 | func (pk *TextPacket) Encode() {
50 | pk.PutByte(pk.TextType)
51 | pk.PutBool(pk.Translation)
52 |
53 | switch pk.TextType {
54 | case Raw, Tip, System:
55 | pk.PutString(pk.Message)
56 | break
57 | case Chat, Whisper, Announcement:
58 | pk.PutString(pk.Source)
59 | pk.PutString(pk.SourceThirdParty)
60 | pk.PutVarInt(pk.SourcePlatform)
61 | pk.PutString(pk.Message)
62 | break
63 | case Translation, Popup, JukeboxPopup:
64 | pk.PutString(pk.Message)
65 | pk.PutUnsignedVarInt(uint32(len(pk.Params)))
66 | for _, v := range pk.Params {
67 | pk.PutString(v)
68 | }
69 | break
70 | }
71 |
72 | pk.PutString(pk.Xuid)
73 | pk.PutString(pk.PlatformChatId)
74 | }
75 |
76 | func (pk *TextPacket) Decode() {
77 | pk.TextType = pk.GetByte()
78 | pk.Translation = pk.GetBool()
79 |
80 | switch pk.TextType {
81 | case Raw, Tip, System:
82 | pk.Message = pk.GetString()
83 | break
84 | case Chat, Whisper, Announcement:
85 | pk.Source = pk.GetString()
86 | pk.SourceThirdParty = pk.GetString()
87 | pk.SourcePlatform = pk.GetVarInt()
88 | pk.Message = pk.GetString()
89 | break
90 | case Translation, Popup, JukeboxPopup:
91 | pk.Message = pk.GetString()
92 | c := pk.GetUnsignedVarInt()
93 | for i := uint32(0); i < c; i++ {
94 | pk.Params = append(pk.Params, pk.GetString())
95 | }
96 | break
97 | }
98 |
99 | pk.Xuid = pk.GetString()
100 | pk.PlatformChatId = pk.GetString()
101 | }
--------------------------------------------------------------------------------
/packets/update_attributes_packet.go:
--------------------------------------------------------------------------------
1 | package packets
2 |
3 | import (
4 | "github.com/Irmine/GoMine/net/packets"
5 | "github.com/irmine/worlds/entities/data"
6 | info2 "github.com/infinitygamers/goproxy/info"
7 | )
8 |
9 | type UpdateAttributesPacket struct {
10 | *packets.Packet
11 | RuntimeId uint64
12 | Attributes data.AttributeMap
13 | }
14 |
15 | func NewUpdateAttributesPacket() *UpdateAttributesPacket {
16 | return &UpdateAttributesPacket{packets.NewPacket(info2.UpdateAttributesPacket), 0, data.NewAttributeMap()}
17 | }
18 |
19 | func (pk *UpdateAttributesPacket) Encode() {
20 | pk.PutEntityRuntimeId(pk.RuntimeId)
21 | pk.PutAttributeMap(pk.Attributes)
22 | }
23 |
24 | func (pk *UpdateAttributesPacket) Decode() {
25 | pk.RuntimeId = pk.GetEntityRuntimeId()
26 | pk.Attributes = pk.GetAttributeMap()
27 | }
28 |
--------------------------------------------------------------------------------
/proxy.go:
--------------------------------------------------------------------------------
1 | package goproxy
2 |
3 | import (
4 | "net"
5 | "os"
6 | "strconv"
7 | )
8 |
9 | type Proxy struct {
10 | *net.UDPConn
11 | Config Config
12 | }
13 |
14 | const (
15 | Prefix = "GoProxy > "
16 | Author = "xBeastMode"
17 | Version = "1.2"
18 | )
19 |
20 | var LogoType = []string{
21 | " _____ _____",
22 | " / ____| | __ \\",
23 | "| | __ ___ | |__) | __ _____ ___ _ ",
24 | "| | |_ |/ _ \\| ___/ '__/ _ \\ \\/ / | | |",
25 | "| |__| | (_) | | | | | (_) > <| |_| |",
26 | " \\_____|\\___/|_| |_| \\___/_/\\_\\\\__, |",
27 | " __/ |",
28 | " |___/ ",
29 | }
30 |
31 | // this function starts the Proxy
32 | // it will start "sniffing" packets
33 | func StartProxy() {
34 | var config = NewConfig()
35 | var proxy = Proxy{Config:config}
36 | var err error
37 |
38 | // forward the Proxy to a custom port
39 | proxy.UDPConn, err = net.ListenUDP("udp", &net.UDPAddr{IP: net.ParseIP(config.BindAddr), Port: config.BindPort})
40 |
41 | if err != nil {
42 | Panic(err.Error())
43 | os.Exit(1)
44 | }
45 |
46 | // just typical console logs
47 | for _, v := range LogoType {
48 | Info(AnsiBrightRed + v)
49 | }
50 | Info(AnsiGreen + Author + "'s Proxy version " + Version)
51 | Info("Starting Proxy on " + config.BindAddr + ":" + strconv.Itoa(config.BindPort))
52 |
53 | if err != nil {
54 | Panic(err.Error())
55 | os.Exit(1)
56 | }
57 |
58 | // looks up the Server domain and returns it address
59 | addrs, err := net.LookupHost(config.ServerAddr)
60 |
61 | if err != nil {
62 | Panic(err.Error())
63 | os.Exit(1)
64 | }
65 |
66 | // resolve Server address
67 | addr, err := net.ResolveUDPAddr("udp", addrs[0] + ":" + strconv.Itoa(config.ServerPort))
68 |
69 | if err != nil {
70 | Panic(err.Error())
71 | os.Exit(1)
72 | }
73 |
74 | // start a new Connection between Server and Client
75 | conn := NewConnection(&proxy)
76 | conn.Server.SetAddress(addr)
77 |
78 | Info("Listening to Server address: " + addrs[0] + ":" + strconv.Itoa(config.ServerPort))
79 |
80 | // start the packet "sniffing" from Client
81 | conn.HandleIncomingPackets()
82 | }
--------------------------------------------------------------------------------
/reliability.go:
--------------------------------------------------------------------------------
1 | package goproxy
2 |
3 | const (
4 | Unreliable = iota + 0x00
5 | UnreliableSequenced
6 | Reliable
7 | ReliableOrdered
8 | ReliableSequenced
9 | UnreliableWithAckReceipt
10 | ReliableWithAckReceipt
11 | ReliableOrderedWithAckReceipt
12 | )
13 |
14 | func isReliable(reliability byte) bool {
15 | return reliability == Reliable || reliability == ReliableOrdered || reliability == ReliableSequenced || reliability == ReliableWithAckReceipt || reliability == ReliableOrderedWithAckReceipt
16 | }
17 |
18 | func isSequenced(reliability byte) bool {
19 | return reliability == UnreliableSequenced || reliability == ReliableSequenced
20 | }
21 |
22 | func isOrdered(reliability byte) bool {
23 | return reliability == ReliableOrdered || reliability == ReliableOrderedWithAckReceipt
24 | }
25 |
26 | func isSequencedOrdered(reliability byte) bool {
27 | return reliability == UnreliableSequenced || reliability == ReliableOrdered || reliability == ReliableSequenced || reliability == ReliableOrderedWithAckReceipt
28 | }
--------------------------------------------------------------------------------
/server.go:
--------------------------------------------------------------------------------
1 | package goproxy
2 |
3 | import (
4 | "net"
5 | "github.com/Irmine/GoMine/net/packets"
6 | )
7 |
8 | type Server struct {
9 | Host // Server extends a host that has writable packets
10 | // Server's udp address
11 | addr *net.UDPAddr
12 | // the main Proxy
13 | Proxy *Proxy
14 | // the Connection between the Server
15 | // and the Client
16 | Conn *Connection
17 | // Server Data contains the Server's query info such as:
18 | // Server name, version, protocol, players, software, etc...
19 | Data ServerData
20 | // the Server's uid
21 | serverId int64
22 | }
23 |
24 |
25 | // returns new Server host
26 | // that has writable packets
27 | func NewServer(proxy *Proxy, conn *Connection) *Server {
28 | server := Server{}
29 | server.Proxy = proxy
30 | server.Conn = conn
31 | server.Data = NewServerData()
32 | return &server
33 | }
34 |
35 | // returns if this host is the client
36 | // this is the server struct to it returns false
37 | func (server Server) IsClient() bool {
38 | return false
39 | }
40 |
41 | // returns if this host is the client
42 | // this is the server struct to it returns true
43 | func (server Server) IsServer() bool {
44 | return true
45 | }
46 |
47 | // this function is from the host interface
48 | // it writes a packet buffer to the Server
49 | func (server Server) WritePacket(buffer []byte) {
50 | _, err := server.Proxy.WriteToUDP(buffer, server.addr)
51 | if err != nil {
52 | Alert(err.Error())
53 | }
54 | }
55 |
56 | // this function is from the host interface
57 | // it sends a single packet
58 | func (server Server) SendPacket(packet packets.IPacket) {
59 | server.SendBatchPacket([]packets.IPacket{packet})
60 | }
61 |
62 | // this function is from the host interface
63 | // it sends a batch packet:
64 | // a packet with multiple packets inside
65 | func (server Server) SendBatchPacket(packets []packets.IPacket) {
66 | datagram := server.Conn.pkHandler.DatagramBuilder.BuildFromPackets(packets)
67 | server.WritePacket(datagram.Buffer)
68 | }
69 |
70 | // this set's the udp address
71 | // which is used to communicate with the Server
72 | func (server *Server) SetAddress(addr *net.UDPAddr) {
73 | server.addr = addr
74 | }
75 |
76 | // returns the Server's address as net.UDPAddr
77 | func (server Server) GetAddress() net.UDPAddr {
78 | return *server.addr
79 | }
80 |
81 | // this returns the Server's Data struct
82 | func (server *Server) GetServerData() ServerData {
83 | return server.GetServerData()
84 | }
--------------------------------------------------------------------------------
/server_data.go:
--------------------------------------------------------------------------------
1 | package goproxy
2 |
3 | import (
4 | "strings"
5 | "strconv"
6 | )
7 |
8 | // this struct holds the Server Data
9 | type ServerData struct {
10 | // raw Server Data as mixed slice
11 | RawData []interface{}
12 | // Server name as string
13 | serverName string
14 | // Server protocol version as int
15 | protocolVersion int
16 | // Server game version as int
17 | gameVersion int
18 | // Server online player count as int
19 | onlinePlayerCount int //ignore
20 | // Server nax player count as int
21 | maxPlayerCount int //ignore
22 | }
23 |
24 | func NewServerData() ServerData {
25 | return ServerData{}
26 | }
27 |
28 | // This parses Data sent from the Server
29 | // the Data is send in this format:
30 | // MCPE;Server name;protocol version;MCPE version;online player count;max player count
31 | func (svData *ServerData) ParseFromString(data string){
32 | split := strings.Split(data, ";")[1:]
33 | svData.serverName = split[0]
34 | svData.protocolVersion, _ = strconv.Atoi(split[1])
35 | svData.gameVersion, _ = strconv.Atoi(split[2])
36 | svData.onlinePlayerCount, _ = strconv.Atoi(split[3])
37 | svData.maxPlayerCount, _ = strconv.Atoi(split[4])
38 | }
39 |
40 | // returns the Server name sent from the Server
41 | func (svData *ServerData) GetServerName() string {
42 | return svData.serverName
43 | }
44 |
45 | // returns the protocol version sent from the Server
46 | func (svData *ServerData) GetProtocolVersion() int {
47 | return svData.protocolVersion
48 | }
49 |
50 | // returns the game version sent from the Server
51 | func (svData *ServerData) GetGameVersion() int {
52 | return svData.gameVersion
53 | }
--------------------------------------------------------------------------------
/start/main.go:
--------------------------------------------------------------------------------
1 | package main
2 |
3 | import (
4 | "github.com/infinitygamers/goproxy"
5 | )
6 |
7 | func main() {
8 | mcpeproxy.StartProxy()
9 | }
10 |
--------------------------------------------------------------------------------