Files
csgowtfd/csgo/sharecode.go

50 lines
1.3 KiB
Go

package csgo
import (
"encoding/binary"
"fmt"
"math/big"
"regexp"
"strings"
)
//goland:noinspection SpellCheckingInspection
var DICT = "ABCDEFGHJKLMNOPQRSTUVWXYZabcdefhijkmnopqrstuvwxyz23456789"
var sharecodeRexEx = regexp.MustCompile("^CSGO(?:-?[\\w]{5}){5}$")
func DecodeSharecode(code string) (uint64, uint64, uint16, error) {
if !sharecodeRexEx.MatchString(code) {
return 0, 0, 0, fmt.Errorf("not a CSGO sharecode: %s", code)
}
cleanCode := strings.ReplaceAll(strings.ReplaceAll(code, "CSGO", ""), "-", "")
chars := ReverseString(strings.Split(cleanCode, ""))
bigInt := new(big.Int)
dictLenBig := big.NewInt(int64(len(DICT)))
for _, c := range chars {
bigInt.Mul(bigInt, dictLenBig)
bigInt.Add(bigInt, big.NewInt(int64(strings.Index(DICT, c))))
}
if bigInt.BitLen() > 144 {
return 0, 0, 0, fmt.Errorf("invalid sharecode")
}
bytes := make([]byte, 18)
bigInt.FillBytes(bytes)
matchId := binary.LittleEndian.Uint64(bytes[0:8])
outcomeId := binary.LittleEndian.Uint64(bytes[8:16])
tokenId := binary.LittleEndian.Uint16(bytes[16:18])
return matchId, outcomeId, tokenId, nil
}
func ReverseString(numbers []string) []string {
for i, j := 0, len(numbers)-1; i < j; i, j = i+1, j-1 {
numbers[i], numbers[j] = numbers[j], numbers[i]
}
return numbers
}