Handle ADDNODE packet
parent
622e5c3889
commit
8a219bb04b
47
blockdata.go
47
blockdata.go
|
@ -14,22 +14,9 @@ const NodeCount = 16 * 16 * 16
|
|||
func processBlockdata(p *Peer, pkt *rudp.Pkt) bool {
|
||||
srv := p.ServerName()
|
||||
|
||||
var zc uint32
|
||||
si := len(pkt.Data) - 1
|
||||
for ; si > 0; si-- {
|
||||
// Check for zlib header
|
||||
if pkt.Data[si] == 120 && (pkt.Data[1+si] == 0x01 || pkt.Data[1+si] == 0x9C || pkt.Data[1+si] == 0xDA) {
|
||||
zc++
|
||||
}
|
||||
}
|
||||
|
||||
if zc == 2 {
|
||||
si = 14
|
||||
// Check for zlib header
|
||||
for ; !(pkt.Data[si] == 120 && (pkt.Data[1+si] == 0x01 || pkt.Data[1+si] == 0x9C || pkt.Data[1+si] == 0xDA)); si++ {
|
||||
}
|
||||
} else {
|
||||
si = len(pkt.Data)
|
||||
si := 14
|
||||
// Check for zlib header
|
||||
for ; !(pkt.Data[si] == 120 && (pkt.Data[1+si] == 0x01 || pkt.Data[1+si] == 0x9C || pkt.Data[1+si] == 0xDA)); si++ {
|
||||
}
|
||||
|
||||
compressedNodes := pkt.Data[13:si]
|
||||
|
@ -64,20 +51,22 @@ func processBlockdata(p *Peer, pkt *rudp.Pkt) bool {
|
|||
|
||||
recompNodes := recompBuf.Bytes()
|
||||
|
||||
if zc == 2 {
|
||||
data := make([]byte, 13+len(recompNodes)+len(pkt.Data[si:]))
|
||||
copy(data[:13], pkt.Data[:13])
|
||||
copy(data[13:13+len(recompNodes)], recompNodes)
|
||||
copy(data[13+len(recompNodes):], pkt.Data[si:])
|
||||
data := make([]byte, 13+len(recompNodes)+len(pkt.Data[si:]))
|
||||
copy(data[:13], pkt.Data[:13])
|
||||
copy(data[13:13+len(recompNodes)], recompNodes)
|
||||
copy(data[13+len(recompNodes):], pkt.Data[si:])
|
||||
|
||||
pkt.Data = data
|
||||
} else {
|
||||
data := make([]byte, 13+len(recompNodes))
|
||||
copy(data[:13], pkt.Data[:13])
|
||||
copy(data[13:], recompNodes)
|
||||
|
||||
pkt.Data = data
|
||||
}
|
||||
pkt.Data = data
|
||||
|
||||
return false
|
||||
}
|
||||
|
||||
func processAddnode(p *Peer, pkt *rudp.Pkt) bool {
|
||||
srv := p.ServerName()
|
||||
|
||||
contentID := binary.BigEndian.Uint16(pkt.Data[8:10])
|
||||
newID := nodeDefs[srv][contentID].ID()
|
||||
binary.BigEndian.PutUint16(pkt.Data[8:10], newID)
|
||||
|
||||
return false
|
||||
}
|
||||
|
|
|
@ -149,6 +149,8 @@ func processPktCommand(src, dst *Peer, pkt *rudp.Pkt) bool {
|
|||
return processRpc(src, *pkt)
|
||||
case ToClientBlockdata:
|
||||
return processBlockdata(dst, pkt)
|
||||
case ToClientAddNode:
|
||||
return processAddnode(dst, pkt)
|
||||
default:
|
||||
return false
|
||||
}
|
||||
|
|
|
@ -0,0 +1,125 @@
|
|||
package main
|
||||
|
||||
import (
|
||||
"bytes"
|
||||
"compress/zlib"
|
||||
"encoding/binary"
|
||||
"io"
|
||||
)
|
||||
|
||||
var itemdef []byte
|
||||
|
||||
type ItemDef struct {
|
||||
name string
|
||||
data []byte
|
||||
}
|
||||
|
||||
// Name returns the name of an ItemDef
|
||||
func (i *ItemDef) Name() string { return i.name }
|
||||
|
||||
// Data returns the actual definition
|
||||
func (i *ItemDef) Data() []byte { return i.data }
|
||||
|
||||
func mergeItemdefs(mgrs [][]byte) error {
|
||||
var itemDefs []*ItemDef
|
||||
aliases := make(map[string]string)
|
||||
|
||||
// Extract definitions from CItemDefManager
|
||||
for _, compressedMgr := range mgrs {
|
||||
zr, err := zlib.NewReader(bytes.NewReader(compressedMgr))
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
buf := &bytes.Buffer{}
|
||||
_, err = io.Copy(buf, zr)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
zr.Close()
|
||||
|
||||
mgr := buf.Bytes()
|
||||
|
||||
count := binary.BigEndian.Uint16(mgr[1:3])
|
||||
|
||||
si := uint32(3)
|
||||
ItemLoop:
|
||||
for i := uint16(0); i < count; i++ {
|
||||
deflen := binary.BigEndian.Uint16(mgr[si : 2+si])
|
||||
def := mgr[2+si : 2+si+uint32(deflen)]
|
||||
|
||||
itemNameLen := binary.BigEndian.Uint16(def[2:4])
|
||||
itemName := string(def[4 : 4+itemNameLen])
|
||||
|
||||
for _, idef := range itemDefs {
|
||||
if idef.Name() == itemName {
|
||||
si += 2 + uint32(deflen)
|
||||
continue ItemLoop
|
||||
}
|
||||
}
|
||||
|
||||
itemDefs = append(itemDefs, &ItemDef{name: itemName, data: def})
|
||||
|
||||
si += 2 + uint32(deflen)
|
||||
}
|
||||
|
||||
aliasCount := binary.BigEndian.Uint16(mgr[si : 2+si])
|
||||
|
||||
si += 2
|
||||
for i := uint16(0); i < aliasCount; i++ {
|
||||
namelen := binary.BigEndian.Uint16(mgr[si : 2+si])
|
||||
name := string(mgr[2+si : 2+si+uint32(namelen)])
|
||||
|
||||
convertlen := binary.BigEndian.Uint16(mgr[2+si+uint32(namelen) : 4+si+uint32(namelen)])
|
||||
convert := string(mgr[4+si+uint32(namelen) : 4+si+uint32(namelen)+uint32(convertlen)])
|
||||
|
||||
if aliases[name] == "" {
|
||||
aliases[name] = convert
|
||||
}
|
||||
|
||||
si += 4 + uint32(namelen) + uint32(convertlen)
|
||||
}
|
||||
}
|
||||
|
||||
// Merge definitions into new CItemDefManager
|
||||
mgr := make([]byte, 3)
|
||||
mgr[0] = uint8(0x00)
|
||||
binary.BigEndian.PutUint16(mgr[1:3], uint16(len(itemDefs)))
|
||||
|
||||
var allDefs []byte
|
||||
for _, def := range itemDefs {
|
||||
defData := make([]byte, 2+len(def.Data()))
|
||||
binary.BigEndian.PutUint16(defData[0:2], uint16(len(def.Data())))
|
||||
copy(defData[2:], def.Data())
|
||||
allDefs = append(allDefs, defData...)
|
||||
}
|
||||
|
||||
mgr = append(mgr, allDefs...)
|
||||
|
||||
aliasCount := make([]byte, 2)
|
||||
binary.BigEndian.PutUint16(aliasCount, uint16(len(aliases)))
|
||||
mgr = append(mgr, aliasCount...)
|
||||
|
||||
for name, convert := range aliases {
|
||||
namelen := make([]byte, 2)
|
||||
binary.BigEndian.PutUint16(namelen, uint16(len(name)))
|
||||
|
||||
convertlen := make([]byte, 2)
|
||||
binary.BigEndian.PutUint16(convertlen, uint16(len(convert)))
|
||||
|
||||
mgr = append(mgr, namelen...)
|
||||
mgr = append(mgr, []byte(name)...)
|
||||
|
||||
mgr = append(mgr, convertlen...)
|
||||
mgr = append(mgr, []byte(convert)...)
|
||||
}
|
||||
|
||||
var compressedMgr bytes.Buffer
|
||||
zw := zlib.NewWriter(&compressedMgr)
|
||||
zw.Write(mgr)
|
||||
zw.Close()
|
||||
|
||||
itemdef = compressedMgr.Bytes()
|
||||
|
||||
return nil
|
||||
}
|
28
media.go
28
media.go
|
@ -14,7 +14,7 @@ import (
|
|||
)
|
||||
|
||||
// MediaRefetchInterval is the amount of time between media downloads
|
||||
const MediaRefetchInterval = 30 * time.Second
|
||||
const MediaRefetchInterval = 10 * time.Minute
|
||||
|
||||
var media map[string]*mediaFile
|
||||
var tooldefs [][]byte
|
||||
|
@ -61,7 +61,7 @@ func (p *Peer) fetchMedia() {
|
|||
case ToClientCraftitemdef:
|
||||
craftitemdefs = append(craftitemdefs, pkt.Data[2:])
|
||||
case ToClientItemdef:
|
||||
itemdefs = append(itemdefs, pkt.Data[2:])
|
||||
itemdefs = append(itemdefs, pkt.Data[6:])
|
||||
case ToClientMovement:
|
||||
movement = pkt.Data[2:]
|
||||
case ToClientDetachedInventory:
|
||||
|
@ -205,19 +205,17 @@ func (p *Peer) announceMedia() {
|
|||
<-ack
|
||||
}
|
||||
|
||||
for _, def := range itemdefs {
|
||||
data := make([]byte, 2+len(def))
|
||||
data[0] = uint8(0x00)
|
||||
data[1] = uint8(ToClientItemdef)
|
||||
copy(data[2:], def)
|
||||
data = make([]byte, 6+len(itemdef))
|
||||
data[0] = uint8(0x00)
|
||||
data[1] = uint8(ToClientItemdef)
|
||||
binary.BigEndian.PutUint32(data[2:6], uint32(len(itemdef)))
|
||||
copy(data[6:], itemdef)
|
||||
|
||||
ack, err := p.Send(rudp.Pkt{Data: data})
|
||||
if err != nil {
|
||||
log.Print(err)
|
||||
continue
|
||||
}
|
||||
<-ack
|
||||
ack, err = p.Send(rudp.Pkt{Data: data})
|
||||
if err != nil {
|
||||
log.Print(err)
|
||||
}
|
||||
<-ack
|
||||
|
||||
p.updateDetachedInvs(srvname)
|
||||
|
||||
|
@ -438,6 +436,10 @@ func loadMedia() {
|
|||
}
|
||||
}
|
||||
|
||||
if err := mergeItemdefs(itemdefs); err != nil {
|
||||
log.Fatal(err)
|
||||
}
|
||||
|
||||
updateMediaCache()
|
||||
}
|
||||
|
||||
|
|
|
@ -38,7 +38,7 @@ func mergeNodedefs(mgrs map[string][]byte) error {
|
|||
|
||||
var nextID uint16
|
||||
|
||||
// Extract definitions from NodeDefMgrs
|
||||
// Extract definitions from NodeDefManagers
|
||||
for srv, compressedMgr := range mgrs {
|
||||
if nodeDefs[srv] == nil {
|
||||
nodeDefs[srv] = make(map[uint16]*NodeDef)
|
||||
|
@ -96,7 +96,7 @@ func mergeNodedefs(mgrs map[string][]byte) error {
|
|||
}
|
||||
}
|
||||
|
||||
// Merge definitions into new NodeDefMgr
|
||||
// Merge definitions into new NodeDefManager
|
||||
mgr := make([]byte, 7)
|
||||
mgr[0] = uint8(1)
|
||||
binary.BigEndian.PutUint16(mgr[1:3], total)
|
||||
|
|
Loading…
Reference in New Issue