Presence Code Python

From Second Life Wiki
Revision as of 21:54, 14 December 2007 by SignpostMarv Martin (talk | contribs) (vertical bar seperator not needed in hyperlinks)
Jump to navigation Jump to search

Extremely incomplete example of how to log an avatar in and establish a presence. So far it only sends enough to temporarily show in-world. More to come....

(based on a sample login script found at libsl login.)

<python>from struct import *
from zerocode import  *
import md5
import xmlrpclib

import re
import httplib, urllib        
from urlparse import urlparse    
import socket, sys, time
import uuid
from makepacketdict import makepacketdict


mypacketdictionary = {}

def login(first, last, passwd, mac):
  passwd_md5 = '$1$' + md5.new(passwd).hexdigest()
 
  uri = 'http://127.0.0.1'
  uri = 'https://login.agni.lindenlab.com/cgi-bin/login.cgi'
  s = xmlrpclib.ServerProxy(uri)
 
  login_details = {
    'first': first,
    'last': last,
    'passwd': passwd_md5,
    'start': 'last',
    'major': '1',
    'minor': '18',
    'patch': '5',
    'build': '3',
    'platform': 'Win',
    'mac': mac,
    'options': [],
    'user-agent': 'sl.py 0.1',
    'id0': '',
    'agree_to_tos': '',
    'viewer_digest': '09d93740-8f37-c418-fbf2-2a78c7b0d1ea'
  }
  return s.login_to_simulator(login_details)




def get_caps(results,cap_key, request_keys):

  _, netloc, path, _, _, _ = urlparse(results[cap_key])

  params = "<llsd><array><string>"+ request_keys[0]+"</string></array></llsd>"
  headers = {"content-type": "application/xml"}
  conn = httplib.HTTPSConnection(netloc)

  conn.request("POST", path, params, headers)
  response = conn.getresponse()


  data = response.read()
  conn.close()
  return data
  
def ExtractCap(cap_result):
  trim_xml = re.compile(r"<key>([a-zA-Z_]+)</key><string>([a-zA-Z_:/0-9-.]+)</string>")
  new_key = trim_xml.search(cap_result).group(1)
  new_cap = trim_xml.search(cap_result).group(2)
  return new_key, new_cap

def establishpresence(host, port, circuit_code):

    sock = socket.socket(socket.AF_INET, socket.SOCK_DGRAM)
#Sending packet UseCircuitCode <-- Inits the connection to the sim.
    data = pack('>BLBL',0x00,0x01,00,0xffff0003) + pack('<L',circuit_code) + uuid.UUID(result["session_id"]).bytes+uuid.UUID(result["agent_id"]).bytes
    sock.sendto(data, (host, port))

#ISending packet CompleteAgentMovement <-- establishes the agent's presence
    data = pack('>BLBL',0x00,0x00,00,0xffff00f9) + uuid.UUID(result["agent_id"]).bytes + uuid.UUID(result["session_id"]).bytes + pack('<L', circuit_code)
    sock.sendto(data, (host, port))

#AgentUpdate
    packed_data_header = pack('>BLB', 0x00,0x000,0x04)
    packed_data_ID = uuid.UUID(result["agent_id"]).bytes + uuid.UUID(result["session_id"]).bytes
    packed_data_QuatRots = pack('>ffff', 0.0,0.0,0.0,0.0)+pack('>ffff', 0.0,0.0,0.0,0.0)  
    packed_data_State = pack('>B', 0x00)
    packed_data_Camera = pack('>fff', 0.0,0.0,0.0)+pack('>fff', 0.0,0.0,0.0)+pack('>fff', 0.0,0.0,0.0)+pack('>fff', 0.0,0.0,0.0)
    packed_data_Flags = pack('>fLB', 0.0,0x00,0x00)

    encoded_packed_data = zero_encode(packed_data_ID+packed_data_QuatRots+packed_data_State+packed_data_State+packed_data_Camera+packed_data_Flags)

    packed_data = packed_data_header + encoded_packed_data
    sock.sendto(packed_data, (host, port))

    buf = 100
    i = 0

    while 1:
        i = i + 1
        data,addr = sock.recvfrom(buf)
        if not data:
            print "Client has exited!"
            break
        else:
            test =  ByteToHex(data).split()
            if test[6] == 'FF':
                if test[7] == 'FF':
                    if test[8] == 'FF':
                        print "Message #", i,"Flags: 0x" + test[0], mypacketdictionary[("Fixed" , int("0x"+ByteToHex(data[8:10]).replace(' ', ''),16))], "0x"+ByteToHex(data[8:10]).replace(' ', '')
                    else:
                        print "Message #", i,"Flags: 0x" + test[0], mypacketdictionary[("Low",int("0x"+ByteToHex(data[8:10]).replace(' ', ''),16))],    "0x"+ByteToHex(data[8:10]).replace(' ', '')
                else:
                    print "Message #", i,"Flags: 0x" + test[0], mypacketdictionary[("Medium", int("0x"+ByteToHex(data[7:8]).replace(' ', ''),16))], "0x"+ByteToHex(data[7:8]).replace(' ', '')
            else:
                print "Message #", i,"Flags: 0x" + test[0], mypacketdictionary[("High", int("0x"+ByteToHex(data[6]), 16))], "0x"+ByteToHex(data[6])
    sock.close()
    return


            
        
result = login("First", "Last", "Password", MAC)

mypacketdictionary = makepacketdict()

myhost = result["sim_ip"]
myport = result["sim_port"]
mycircuit_code = result["circuit_code"]

establishpresence(myhost, myport, mycircuit_code)

#cap_out = get_caps(result,"seed_capability", ["ChatSessionRequest"])</python>