Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(12)

Side by Side Diff: third_party/twisted_8_1/twisted/words/protocols/toc.py

Issue 12261012: Remove third_party/twisted_8_1 (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/tools/build
Patch Set: Created 7 years, 10 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
OLDNEW
(Empty)
1 # -*- test-case-name: twisted.words.test -*-
2 # Copyright (c) 2001-2005 Twisted Matrix Laboratories.
3 # See LICENSE for details.
4
5
6 """
7 Implements a AOL Instant Messenger TOC server and client, using the Twisted
8 framework.
9
10 TODO:
11 info,dir: see how gaim connects for this...it may never work if it tries to
12 connect to the aim server automatically
13
14 This module is deprecated.
15
16 Maintainer: U{Paul Swartz<mailto:z3p@twistedmatrix.com>}
17 """
18
19 # twisted imports
20 from twisted.internet import reactor, protocol
21 from twisted.python import log
22
23 # base imports
24 import struct
25 import string
26 import time
27 import base64
28 import os
29 import StringIO
30
31 SIGNON,DATA,ERROR,SIGNOFF,KEEP_ALIVE=range(1,6)
32 PERMITALL,DENYALL,PERMITSOME,DENYSOME=range(1,5)
33
34 DUMMY_CHECKSUM = -559038737 # 0xdeadbeef
35
36 def quote(s):
37 rep=['\\','$','{','}','[',']','(',')','"']
38 for r in rep:
39 s=string.replace(s,r,"\\"+r)
40 return "\""+s+"\""
41
42 def unquote(s):
43 if s=="": return ""
44 if s[0]!='"': return s
45 r=string.replace
46 s=s[1:-1]
47 s=r(s,"\\\\","\\")
48 s=r(s,"\\$","$")
49 s=r(s,"\\{","{")
50 s=r(s,"\\}","}")
51 s=r(s,"\\[","[")
52 s=r(s,"\\]","]")
53 s=r(s,"\\(","(")
54 s=r(s,"\\)",")")
55 s=r(s,"\\\"","\"")
56 return s
57
58 def unquotebeg(s):
59 for i in range(1,len(s)):
60 if s[i]=='"' and s[i-1]!='\\':
61 q=unquote(s[:i+1])
62 return [q,s[i+2:]]
63
64 def unroast(pw):
65 roaststring="Tic/Toc"
66 pw=string.lower(pw[2:])
67 r=""
68 count=0
69 hex=["0","1","2","3","4","5","6","7","8","9","a","b","c","d","e","f"]
70 while pw:
71 st,pw=pw[:2],pw[2:]
72 value=(16*hex.index(st[0]))+hex.index(st[1])
73 xor=ord(roaststring[count])
74 count=(count+1)%len(roaststring)
75 r=r+chr(value^xor)
76 return r
77
78 def roast(pw):
79 # contributed by jemfinch on #python
80 key="Tic/Toc"
81 ro="0x"
82 i=0
83 ascii=map(ord,pw)
84 for c in ascii:
85 ro=ro+'%02x'%(c^ord(key[i%len(key)]))
86 i=i+1
87 return string.lower(ro)
88
89 def checksum(b):
90 return DUMMY_CHECKSUM # do it like gaim does, since the checksum
91 # formula doesn't work
92 ## # used in file transfers
93 ## check0 = check1 = 0x00ff
94 ## for i in range(len(b)):
95 ## if i%2:
96 ## if ord(b[i])>check1:
97 ## check1=check1+0x100 # wrap
98 ## if check0==0:
99 ## check0=0x00ff
100 ## if check1==0x100:
101 ## check1=check1-1
102 ## else:
103 ## check0=check0-1
104 ## check1=check1-ord(b[i])
105 ## else:
106 ## if ord(b[i])>check0: # wrap
107 ## check0=check0+0x100
108 ## if check1==0:
109 ## check1=0x00ff
110 ## if check0==0x100:
111 ## check0=check0-1
112 ## else:
113 ## check1=check1-1
114 ## check0=check0-ord(b[i])
115 ## check0=check0 & 0xff
116 ## check1=check1 & 0xff
117 ## checksum=(long(check0)*0x1000000)+(long(check1)*0x10000)
118 ## return checksum
119
120 def checksum_file(f):
121 return DUMMY_CHECKSUM # do it like gaim does, since the checksum
122 # formula doesn't work
123 ## check0=check1=0x00ff
124 ## i=0
125 ## while 1:
126 ## b=f.read()
127 ## if not b: break
128 ## for char in b:
129 ## i=not i
130 ## if i:
131 ## if ord(char)>check1:
132 ## check1=check1+0x100 # wrap
133 ## if check0==0:
134 ## check0=0x00ff
135 ## if check1==0x100:
136 ## check1=check1-1
137 ## else:
138 ## check0=check0-1
139 ## check1=check1-ord(char)
140 ## else:
141 ## if ord(char)>check0: # wrap
142 ## check0=check0+0x100
143 ## if check1==0:
144 ## check1=0x00ff
145 ## if check0==0x100:
146 ## check0=check0-1
147 ## else:
148 ## check1=check1-1
149 ## check0=check0-ord(char)
150 ## check0=check0 & 0xff
151 ## check1=check1 & 0xff
152 ## checksum=(long(check0)*0x1000000)+(long(check1)*0x10000)
153 ## return checksum
154
155 def normalize(s):
156 s=string.lower(s)
157 s=string.replace(s," ","")
158 return s
159
160
161 class TOCParseError(ValueError):
162 pass
163
164
165 class TOC(protocol.Protocol):
166 users={}
167
168 def connectionMade(self):
169 # initialization of protocol
170 self._buf=""
171 self._ourseqnum=0L
172 self._theirseqnum=0L
173 self._mode="Flapon"
174 self._onlyflaps=0
175 self._laststatus={} # the last status for a user
176 self.username=None
177 self.permitmode=PERMITALL
178 self.permitlist=[]
179 self.denylist=[]
180 self.buddylist=[]
181 self.signontime=0
182 self.idletime=0
183 self.userinfo="<br>"
184 self.userclass=" O"
185 self.away=""
186 self.saved=None
187
188 def _debug(self,data):
189 log.msg(data)
190
191 def connectionLost(self, reason):
192 self._debug("dropped connection from %s" % self.username)
193 try:
194 del self.factory.users[self.username]
195 except:
196 pass
197 for k in self.factory.chatroom.keys():
198 try:
199 self.factory.chatroom[k].leave(self)
200 except TOCParseError:
201 pass
202 if self.saved:
203 self.factory.savedusers[self.username]=self.saved
204 self.updateUsers()
205
206 def sendFlap(self,type,data):
207 """
208 send a FLAP to the client
209 """
210 send="*"
211 self._debug(data)
212 if type==DATA:
213 data=data+"\000"
214 length=len(data)
215 send=send+struct.pack("!BHH",type,self._ourseqnum,length)
216 send=send+data
217 self._ourseqnum=self._ourseqnum+1
218 if self._ourseqnum>(256L**4):
219 self._ourseqnum=0
220 self.transport.write(send)
221
222 def dataReceived(self,data):
223 self._buf=self._buf+data
224 try:
225 func=getattr(self,"mode%s"%self._mode)
226 except:
227 return
228 self._mode=func()
229 if self._onlyflaps and self.isFlap(): self.dataReceived("")
230
231 def isFlap(self):
232 """
233 tests to see if a flap is actually on the buffer
234 """
235 if self._buf=='': return 0
236 if self._buf[0]!="*": return 0
237 if len(self._buf)<6: return 0
238 foo,type,seqnum,length=struct.unpack("!BBHH",self._buf[:6])
239 if type not in range(1,6): return 0
240 if len(self._buf)<6+length: return 0
241 return 1
242
243 def readFlap(self):
244 """
245 read the first FLAP off self._buf, raising errors if it isn't in the rig ht form.
246 the FLAP is the basic TOC message format, and is logically equivilant to a packet in TCP
247 """
248 if self._buf=='': return None
249 if self._buf[0]!="*":
250 raise TOCParseError
251 if len(self._buf)<6: return None
252 foo,type,seqnum,length=struct.unpack("!BBHH",self._buf[:6])
253 if len(self._buf)<6+length: return None
254 data=self._buf[6:6+length]
255 self._buf=self._buf[6+length:]
256 if data and data[-1]=="\000":
257 data=data[:-1]
258 self._debug([type,data])
259 return [type,data]
260
261 #def modeWeb(self):
262 # try:
263 # line,rest=string.split(self._buf,"\n",1)
264 # get,username,http=string.split(line," ",2)
265 # except:
266 # return "Web" # not enough data
267 # foo,type,username=string.split(username,"/")
268 # if type=="info":
269 # user=self.factory.users[username]
270 # text="<HTML><HEAD><TITLE>User Information for %s</TITLE></HEAD><BOD Y>Username: <B>%s</B><br>\nWarning Level: <B>%s%</B><br>\n Online Since: <B>%s</ B><br>\nIdle Minutes: <B>%s</B><br>\n<hr><br>\n%s\n<hr><br>\n"%(user.saved.nick, user.saved.nick, user.saved.evilness, time.asctime(user.signontime), int((time. time()-user.idletime)/60), user.userinfo)
271 # self.transport.write("HTTP/1.1 200 OK\n")
272 # self.transport.write("Content-Type: text/html\n")
273 # self.transport.write("Content-Length: %s\n\n"%len(text))
274 # self.transport.write(text)
275 # self.loseConnection()
276
277 def modeFlapon(self):
278 #if self._buf[:3]=="GET": self.modeWeb() # TODO: get this working
279 if len(self._buf)<10: return "Flapon" # not enough bytes
280 flapon,self._buf=self._buf[:10],self._buf[10:]
281 if flapon!="FLAPON\r\n\r\n":
282 raise TOCParseError
283 self.sendFlap(SIGNON,"\000\000\000\001")
284 self._onlyflaps=1
285 return "Signon"
286
287 def modeSignon(self):
288 flap=self.readFlap()
289 if flap==None:
290 return "Signon"
291 if flap[0]!=SIGNON: raise TOCParseError
292 version,tlv,unlength=struct.unpack("!LHH",flap[1][:8])
293 if version!=1 or tlv!=1 or unlength+8!=len(flap[1]):
294 raise TOCParseError
295 self.username=normalize(flap[1][8:])
296 if self.username in self.factory.savedusers.keys():
297 self.saved=self.factory.savedusers[self.username]
298 else:
299 self.saved=SavedUser()
300 self.saved.nick=self.username
301 return "TocSignon"
302
303 def modeTocSignon(self):
304 flap=self.readFlap()
305 if flap==None:
306 return "TocSignon"
307 if flap[0]!=DATA: raise TOCParseError
308 data=string.split(flap[1]," ")
309 if data[0]!="toc_signon": raise TOCParseError
310 for i in data:
311 if not i:data.remove(i)
312 password=unroast(data[4])
313 if not(self.authorize(data[1],int(data[2]),data[3],password)):
314 self.sendError(BAD_NICKNAME)
315 self.transport.loseConnection()
316 return
317 self.sendFlap(DATA,"SIGN_ON:TOC1.0")
318 self.sendFlap(DATA,"NICK:%s"%self.saved.nick)
319 self.sendFlap(DATA,"CONFIG:%s"%self.saved.config)
320 # sending user configuration goes here
321 return "Connected"
322
323 def authorize(self,server,port,username,password):
324 if self.saved.password=="":
325 self.saved.password=password
326 return 1
327 else:
328 return self.saved.password==password
329
330 def modeConnected(self):
331 flap=self.readFlap()
332 while flap!=None:
333 if flap[0] not in [DATA,KEEP_ALIVE]: raise TOCParseError
334 flapdata=string.split(flap[1]," ",1)
335 tocname=flapdata[0][4:]
336 if len(flapdata)==2:
337 data=flapdata[1]
338 else:
339 data=""
340 func=getattr(self,"toc_"+tocname,None)
341 if func!=None:
342 func(data)
343 else:
344 self.toc_unknown(tocname,data)
345 flap=self.readFlap()
346 return "Connected"
347
348 def toc_unknown(self,tocname,data):
349 self._debug("unknown! %s %s" % (tocname,data))
350
351 def toc_init_done(self,data):
352 """
353 called when all the setup is done.
354
355 toc_init_done
356 """
357 self.signontime=int(time.time())
358 self.factory.users[self.username]=self
359 self.updateUsers()
360
361 def toc_add_permit(self,data):
362 """
363 adds users to the permit list. if the list is null, then set the mode t o DENYALL
364 """
365 if data=="":
366 self.permitmode=DENYALL
367 self.permitlist=[]
368 self.denylist=[]
369 else:
370 self.permitmode=PERMITSOME
371 self.denylist=[]
372 users=string.split(data," ")
373 map(self.permitlist.append,users)
374 self.updateUsers()
375
376 def toc_add_deny(self,data):
377 """
378 adds users to the deny list. if the list is null, then set the mode to PERMITALL
379 """
380 if data=="":
381 self.permitmode=PERMITALL
382 self.permitlist=[]
383 self.denylist=[]
384 else:
385 self.permitmode=DENYSOME
386 self.permitlist=[]
387 users=string.split(data," ")
388 map(self.denylist.append,users)
389 self.updateUsers()
390
391 def toc_evil(self,data):
392 """
393 warns a user.
394
395 toc_evil <username> <anon|norm>
396 """
397 username,nora=string.split(data," ")
398 if nora=="anon":
399 user=""
400 else:
401 user=self.saved.nick
402 if not(self.factory.users.has_key(username)):
403 self.sendError(CANT_WARN,username)
404 return
405 if self.factory.users[username].saved.evilness>=100:
406 self.sendError(CANT_WARN,username)
407 return
408 self.factory.users[username].evilFrom(user)
409
410 def toc_add_buddy(self,data):
411 """
412 adds users to the buddy list
413
414 toc_add_buddy <buddyname1> [<buddyname2>] [<buddyname3>]...
415 """
416 buddies=map(normalize,string.split(data," "))
417 for b in buddies:
418 if b not in self.buddylist:
419 self.buddylist.append(b)
420 for buddy in buddies:
421 try:
422 buddy=self.factory.users[buddy]
423 except:
424 pass
425 else:
426 self.buddyUpdate(buddy)
427
428 def toc_remove_buddy(self,data):
429 """
430 removes users from the buddy list
431
432 toc_remove_buddy <buddyname1> [<buddyname2>] [<buddyname3>]...
433 """
434 buddies=string.split(data," ")
435 for buddy in buddies:
436 try:
437 self.buddylist.remove(normalize(buddy))
438 except: pass
439
440 def toc_send_im(self,data):
441 """
442 incoming instant message
443
444 toc_send_im <screenname> <quoted message> [auto]
445 """
446 username,data=string.split(data," ",1)
447 auto=0
448 if data[-4:]=="auto":
449 auto=1
450 data=data[:-5]
451 data=unquote(data)
452 if not(self.factory.users.has_key(username)):
453 self.sendError(NOT_AVAILABLE,username)
454 return
455 user=self.factory.users[username]
456 if not(self.canContact(user)):
457 self.sendError(NOT_AVAILABLE,username)
458 return
459 user.hearWhisper(self,data,auto)
460
461 def toc_set_info(self,data):
462 """
463 set the users information, retrivable with toc_get_info
464
465 toc_set_info <user info (quoted)>
466 """
467 info=unquote(data)
468 self._userinfo=info
469
470 def toc_set_idle(self,data):
471 """
472 set/unset idle
473
474 toc_set_idle <seconds>
475 """
476 seconds=int(data)
477 self.idletime=time.time()-seconds # time when they started being idle
478 self.updateUsers()
479
480 def toc_set_away(self,data):
481 """
482 set/unset away message
483
484 toc_set_away [<away message>]
485 """
486 away=unquote(data)
487 if not self.away and away: # setting an away message
488 self.away=away
489 self.userclass=self.userclass+'U'
490 self.updateUsers()
491 elif self.away and not away: # coming back
492 self.away=""
493 self.userclass=self.userclass[:2]
494 self.updateUsers()
495 else:
496 raise TOCParseError
497
498 def toc_chat_join(self,data):
499 """
500 joins the chat room.
501
502 toc_chat_join <exchange> <room name>
503 """
504 exchange,name=string.split(data," ",1)
505 self.factory.getChatroom(int(exchange),unquote(name)).join(self)
506
507 def toc_chat_invite(self,data):
508 """
509 invite others to the room.
510
511 toc_chat_invite <room id> <invite message> <buddy 1> [<buddy2>]...
512 """
513 id,data=string.split(data," ",1)
514 id=int(id)
515 message,data=unquotebeg(data)
516 buddies=string.split(data," ")
517 for b in buddies:
518 room=self.factory.chatroom[id]
519 bud=self.factory.users[b]
520 bud.chatInvite(room,self,message)
521
522 def toc_chat_accept(self,data):
523 """
524 accept an invitation.
525
526 toc_chat_accept <room id>
527 """
528 id=int(data)
529 self.factory.chatroom[id].join(self)
530
531 def toc_chat_send(self,data):
532 """
533 send a message to the chat room.
534
535 toc_chat_send <room id> <message>
536 """
537 id,message=string.split(data," ",1)
538 id=int(id)
539 message=unquote(message)
540 self.factory.chatroom[id].say(self,message)
541
542 def toc_chat_whisper(self,data):
543 id,user,message=string.split(data," ",2)
544 id=int(id)
545 room=self.factory.chatroom[id]
546 message=unquote(message)
547 self.factory.users[user].chatWhisper(room,self,message)
548
549 def toc_chat_leave(self,data):
550 """
551 leave the room.
552
553 toc_chat_leave <room id>
554 """
555 id=int(data)
556 self.factory.chatroom[id].leave(self)
557
558 def toc_set_config(self,data):
559 """
560 set the saved config. this gets send when you log in.
561
562 toc_set_config <config>
563 """
564 self.saved.config=unquote(data)
565
566 def toc_get_info(self,data):
567 """
568 get the user info for a user
569
570 toc_get_info <username>
571 """
572 if not self.factory.users.has_key(data):
573 self.sendError(901,data)
574 return
575 self.sendFlap(2,"GOTO_URL:TIC:info/%s"%data)
576
577 def toc_format_nickname(self,data):
578 """
579 change the format of your nickname.
580
581 toc_format_nickname <new format>
582 """
583 # XXX may not work
584 nick=unquote(data)
585 if normalize(nick)==self.username:
586 self.saved.nick=nick
587 self.sendFlap(2,"ADMIN_NICK_STATUS:0")
588 else:
589 self.sendError(BAD_INPUT)
590
591 def toc_change_passwd(self,data):
592 orig,data=unquotebeg(data)
593 new=unquote(data)
594 if orig==self.saved.password:
595 self.saved.password=new
596 self.sendFlap(2,"ADMIN_PASSWD_STATUS:0")
597 else:
598 self.sendError(BAD_INPUT)
599
600 def sendError(self,code,*varargs):
601 """
602 send an error to the user. listing of error messages is below.
603 """
604 send="ERROR:%s"%code
605 for v in varargs:
606 send=send+":"+v
607 self.sendFlap(DATA,send)
608
609 def updateUsers(self):
610 """
611 Update the users who have us on their buddylist.
612 Called when the user changes anything (idle,away) so people can get upda tes.
613 """
614 for user in self.factory.users.values():
615 if self.username in user.buddylist and self.canContact(user):
616 user.buddyUpdate(self)
617
618 def getStatus(self,user):
619 if self.canContact(user):
620 if self in self.factory.users.values():ol='T'
621 else: ol='F'
622 idle=0
623 if self.idletime:
624 idle=int((time.time()-self.idletime)/60)
625 return (self.saved.nick,ol,self.saved.evilness,self.signontime,idle, self.userclass)
626 else:
627 return (self.saved.nick,'F',0,0,0,self.userclass)
628
629 def canContact(self,user):
630 if self.permitmode==PERMITALL: return 1
631 elif self.permitmode==DENYALL: return 0
632 elif self.permitmode==PERMITSOME:
633 if user.username in self.permitlist: return 1
634 else: return 0
635 elif self.permitmode==DENYSOME:
636 if user.username in self.denylist: return 0
637 else: return 1
638 else:
639 assert 0,"bad permitmode %s" % self.permitmode
640
641 def buddyUpdate(self,user):
642 """
643 Update the buddy. Called from updateUsers()
644 """
645 if not self.canContact(user): return
646 status=user.getStatus(self)
647 if not self._laststatus.has_key(user):
648 self._laststatus[user]=()
649 if self._laststatus[user]!=status:
650 send="UPDATE_BUDDY:%s:%s:%s:%s:%s:%s"%status
651 self.sendFlap(DATA,send)
652 self._laststatus[user]=status
653
654 def hearWhisper(self,user,data,auto=0):
655 """
656 Called when you get an IM. If auto=1, it's an autoreply from an away me ssage.
657 """
658 if not self.canContact(user): return
659 if auto: auto='T'
660 else: auto='F'
661 send="IM_IN:%s:%s:%s"%(user.saved.nick,auto,data)
662 self.sendFlap(DATA,send)
663
664 def evilFrom(self,user):
665 if user=="":
666 percent=0.03
667 else:
668 percent=0.1
669 self.saved.evilness=self.saved.evilness+int((100-self.saved.evilness)*pe rcent)
670 self.sendFlap(2,"EVILED:%s:%s"%(self.saved.evilness,user))
671 self.updateUsers()
672
673 def chatJoin(self,room):
674 self.sendFlap(2,"CHAT_JOIN:%s:%s"%(room.id,room.name))
675 f="CHAT_UPDATE_BUDDY:%s:T"%room.id
676 for u in room.users:
677 if u!=self:
678 u.chatUserUpdate(room,self)
679 f=f+":"+u.saved.nick
680 self.sendFlap(2,f)
681
682 def chatInvite(self,room,user,message):
683 if not self.canContact(user): return
684 self.sendFlap(2,"CHAT_INVITE:%s:%s:%s:%s"%(room.name,room.id,user.saved. nick,message))
685
686 def chatUserUpdate(self,room,user):
687 if user in room.users:
688 inroom='T'
689 else:
690 inroom='F'
691 self.sendFlap(2,"CHAT_UPDATE_BUDDY:%s:%s:%s"%(room.id,inroom,user.saved. nick))
692
693 def chatMessage(self,room,user,message):
694 if not self.canContact(user): return
695 self.sendFlap(2,"CHAT_IN:%s:%s:F:%s"%(room.id,user.saved.nick,message))
696
697 def chatWhisper(self,room,user,message):
698 if not self.canContact(user): return
699 self.sendFlap(2,"CHAT_IN:%s:%s:T:%s"%(room.id,user.saved.nick,message))
700
701 def chatLeave(self,room):
702 self.sendFlap(2,"CHAT_LEFT:%s"%(room.id))
703
704
705 class Chatroom:
706 def __init__(self,fac,exchange,name,id):
707 self.exchange=exchange
708 self.name=name
709 self.id=id
710 self.factory=fac
711 self.users=[]
712
713 def join(self,user):
714 if user in self.users:
715 return
716 self.users.append(user)
717 user.chatJoin(self)
718
719 def leave(self,user):
720 if user not in self.users:
721 raise TOCParseError
722 self.users.remove(user)
723 user.chatLeave(self)
724 for u in self.users:
725 u.chatUserUpdate(self,user)
726 if len(self.users)==0:
727 self.factory.remChatroom(self)
728
729 def say(self,user,message):
730 for u in self.users:
731 u.chatMessage(self,user,message)
732
733
734 class SavedUser:
735 def __init__(self):
736 self.config=""
737 self.nick=""
738 self.password=""
739 self.evilness=0
740
741
742 class TOCFactory(protocol.Factory):
743 def __init__(self):
744 self.users={}
745 self.savedusers={}
746 self.chatroom={}
747 self.chatroomid=0
748
749 def buildProtocol(self,addr):
750 p=TOC()
751 p.factory=self
752 return p
753
754 def getChatroom(self,exchange,name):
755 for i in self.chatroom.values():
756 if normalize(i.name)==normalize(name):
757 return i
758 self.chatroom[self.chatroomid]=Chatroom(self,exchange,name,self.chatroom id)
759 self.chatroomid=self.chatroomid+1
760 return self.chatroom[self.chatroomid-1]
761
762 def remChatroom(self,room):
763 id=room.id
764 del self.chatroom[id]
765
766 MAXARGS={}
767 MAXARGS["CONFIG"]=0
768 MAXARGS["NICK"]=0
769 MAXARGS["IM_IN"]=2
770 MAXARGS["UPDATE_BUDDY"]=5
771 MAXARGS["ERROR"]=-1
772 MAXARGS["EVILED"]=1
773 MAXARGS["CHAT_JOIN"]=1
774 MAXARGS["CHAT_IN"]=3
775 MAXARGS["CHAT_UPDATE_BUDDY"]=-1
776 MAXARGS["CHAT_INVITE"]=3
777 MAXARGS["CHAT_LEFT"]=0
778 MAXARGS["ADMIN_NICK_STATUS"]=0
779 MAXARGS["ADMIN_PASSWD_STATUS"]=0
780
781
782 class TOCClient(protocol.Protocol):
783 def __init__(self,username,password,authhost="login.oscar.aol.com",authport= 5190):
784
785 self.username=normalize(username) # our username
786 self._password=password # our password
787 self._mode="SendNick" # current mode
788 self._ourseqnum=19071 # current sequence number (for sendFlap)
789 self._authhost=authhost # authorization host
790 self._authport=authport # authorization port
791 self._online=0 # are we online?
792 self._buddies=[] # the current buddy list
793 self._privacymode=PERMITALL # current privacy mode
794 self._permitlist=[] # list of users on the permit list
795 self._roomnames={} # the names for each of the rooms we're in
796 self._receivedchatmembers={} # have we gotten who's in our room yet?
797 self._denylist=[]
798 self._cookies={} # for file transfers
799 self._buf='' # current data buffer
800 self._awaymessage=''
801
802 def _debug(self,data):
803 log.msg(data)
804
805 def sendFlap(self,type,data):
806 if type==DATA:
807 data=data+"\000"
808 length=len(data)
809 s="*"
810 s=s+struct.pack("!BHH",type,self._ourseqnum,length)
811 s=s+data
812 self._ourseqnum=self._ourseqnum+1
813 if self._ourseqnum>(256*256+256):
814 self._ourseqnum=0
815 self._debug(data)
816 self.transport.write(s)
817
818 def isFlap(self):
819 """
820 tests to see if a flap is actually on the buffer
821 """
822 if self._buf=='': return 0
823 if self._buf[0]!="*": return 0
824 if len(self._buf)<6: return 0
825 foo,type,seqnum,length=struct.unpack("!BBHH",self._buf[:6])
826 if type not in range(1,6): return 0
827 if len(self._buf)<6+length: return 0
828 return 1
829
830 def readFlap(self):
831 if self._buf=='': return None
832 if self._buf[0]!="*":
833 raise TOCParseError
834 if len(self._buf)<6: return None
835 foo,type,seqnum,length=struct.unpack("!BBHH",self._buf[:6])
836 if len(self._buf)<6+length: return None
837 data=self._buf[6:6+length]
838 self._buf=self._buf[6+length:]
839 if data and data[-1]=="\000":
840 data=data[:-1]
841 return [type,data]
842
843 def connectionMade(self):
844 self._debug("connection made! %s" % self.transport)
845 self.transport.write("FLAPON\r\n\r\n")
846
847 def connectionLost(self, reason):
848 self._debug("connection lost!")
849 self._online=0
850
851 def dataReceived(self,data):
852 self._buf=self._buf+data
853 while self.isFlap():
854 flap=self.readFlap()
855 func=getattr(self,"mode%s"%self._mode)
856 func(flap)
857
858 def modeSendNick(self,flap):
859 if flap!=[1,"\000\000\000\001"]: raise TOCParseError
860 s="\000\000\000\001\000\001"+struct.pack("!H",len(self.username))+self.u sername
861 self.sendFlap(1,s)
862 s="toc_signon %s %s %s %s english \"penguin\""%(self._authhost,\
863 self._authport,self.username,roast(self._password))
864 self.sendFlap(2,s)
865 self._mode="Data"
866
867 def modeData(self,flap):
868 if not flap[1]:
869 return
870 if not ':' in flap[1]:
871 self._debug("bad SNAC:%s"%(flap[1]))
872 return
873 command,rest=string.split(flap[1],":",1)
874 if MAXARGS.has_key(command):
875 maxsplit=MAXARGS[command]
876 else:
877 maxsplit=-1
878 if maxsplit==-1:
879 l=tuple(string.split(rest,":"))
880 elif maxsplit==0:
881 l=(rest,)
882 else:
883 l=tuple(string.split(rest,":",maxsplit))
884 self._debug("%s %s"%(command,l))
885 try:
886 func=getattr(self,"toc%s"%command)
887 self._debug("calling %s"%func)
888 except:
889 self._debug("calling %s"%self.tocUNKNOWN)
890 self.tocUNKNOWN(command,l)
891 return
892 func(l)
893
894 def tocUNKNOWN(self,command,data):
895 pass
896
897 def tocSIGN_ON(self,data):
898 if data!=("TOC1.0",): raise TOCParseError
899 self._debug("Whee, signed on!")
900 if self._buddies: self.add_buddy(self._buddies)
901 self._online=1
902 self.onLine()
903
904 def tocNICK(self,data):
905 """
906 Handle a message that looks like::
907
908 NICK:<format of nickname>
909 """
910 self.username=data[0]
911
912 def tocCONFIG(self,data):
913 """
914 Handle a message that looks like::
915
916 CONFIG:<config>
917
918 Format of config data:
919
920 - g: group. all users until next g or end of config are in this gro up
921 - b: buddy
922 - p: person on the permit list
923 - d: person on the deny list
924 - m: permit/deny mode (1: permit all, 2: deny all, 3: permit some, 4 : deny some)
925 """
926 data=data[0]
927 if data and data[0]=="{":data=data[1:-1]
928 lines=string.split(data,"\n")
929 buddylist={}
930 currentgroup=""
931 permit=[]
932 deny=[]
933 mode=1
934 for l in lines:
935 if l:
936 code,data=l[0],l[2:]
937 if code=='g': # group
938 currentgroup=data
939 buddylist[currentgroup]=[]
940 elif code=='b':
941 buddylist[currentgroup].append(data)
942 elif code=='p':
943 permit.append(data)
944 elif code=='d':
945 deny.append(data)
946 elif code=='m':
947 mode=int(data)
948 self.gotConfig(mode,buddylist,permit,deny)
949
950 def tocIM_IN(self,data):
951 """
952 Handle a message that looks like::
953
954 IM_IN:<user>:<autoreply T|F>:message
955 """
956 user=data[0]
957 autoreply=(data[1]=='T')
958 message=data[2]
959 self.hearMessage(user,message,autoreply)
960
961 def tocUPDATE_BUDDY(self,data):
962 """
963 Handle a message that looks like::
964
965 UPDATE_BUDDY:<username>:<online T|F>:<warning level>:<signon time>:< idle time (minutes)>:<user class>
966 """
967 data=list(data)
968 online=(data[1]=='T')
969 if len(data[5])==2:
970 data[5]=data[5]+" "
971 away=(data[5][-1]=='U')
972 if data[5][-1]=='U':
973 data[5]=data[5][:-1]
974 self.updateBuddy(data[0],online,int(data[2]),int(data[3]),int(data[4]),d ata[5],away)
975
976 def tocERROR(self,data):
977 """
978 Handle a message that looks like::
979
980 ERROR:<error code>:<misc. data>
981 """
982 code,args=data[0],data[1:]
983 self.hearError(int(code),args)
984
985 def tocEVILED(self,data):
986 """
987 Handle a message that looks like::
988
989 EVILED:<current warning level>:<user who warned us>
990 """
991 self.hearWarning(data[0],data[1])
992
993 def tocCHAT_JOIN(self,data):
994 """
995 Handle a message that looks like::
996
997 CHAT_JOIN:<room id>:<room name>
998 """
999 #self.chatJoined(int(data[0]),data[1])
1000 self._roomnames[int(data[0])]=data[1]
1001 self._receivedchatmembers[int(data[0])]=0
1002
1003 def tocCHAT_UPDATE_BUDDY(self,data):
1004 """
1005 Handle a message that looks like::
1006
1007 CHAT_UPDATE_BUDDY:<room id>:<in room? T/F>:<user 1>:<user 2>...
1008 """
1009 roomid=int(data[0])
1010 inroom=(data[1]=='T')
1011 if self._receivedchatmembers[roomid]:
1012 for u in data[2:]:
1013 self.chatUpdate(roomid,u,inroom)
1014 else:
1015 self._receivedchatmembers[roomid]=1
1016 self.chatJoined(roomid,self._roomnames[roomid],list(data[2:]))
1017
1018 def tocCHAT_IN(self,data):
1019 """
1020 Handle a message that looks like::
1021
1022 CHAT_IN:<room id>:<username>:<whisper T/F>:<message>
1023
1024 whisper isn't used
1025 """
1026 whisper=(data[2]=='T')
1027 if whisper:
1028 self.chatHearWhisper(int(data[0]),data[1],data[3])
1029 else:
1030 self.chatHearMessage(int(data[0]),data[1],data[3])
1031
1032 def tocCHAT_INVITE(self,data):
1033 """
1034 Handle a message that looks like::
1035
1036 CHAT_INVITE:<room name>:<room id>:<username>:<message>
1037 """
1038 self.chatInvited(int(data[1]),data[0],data[2],data[3])
1039
1040 def tocCHAT_LEFT(self,data):
1041 """
1042 Handle a message that looks like::
1043
1044 CHAT_LEFT:<room id>
1045 """
1046 self.chatLeft(int(data[0]))
1047 del self._receivedchatmembers[int(data[0])]
1048 del self._roomnames[int(data[0])]
1049
1050 def tocRVOUS_PROPOSE(self,data):
1051 """
1052 Handle a message that looks like::
1053
1054 RVOUS_PROPOSE:<user>:<uuid>:<cookie>:<seq>:<rip>:<pip>:<vip>:<port>
1055 [:tlv tag1:tlv value1[:tlv tag2:tlv value2[:...]]]
1056 """
1057 user,uid,cookie,seq,rip,pip,vip,port=data[:8]
1058 cookie=base64.decodestring(cookie)
1059 port=int(port)
1060 tlvs={}
1061 for i in range(8,len(data),2):
1062 key=data[i]
1063 value=base64.decodestring(data[i+1])
1064 tlvs[key]=value
1065 name=UUIDS[uid]
1066 try:
1067 func=getattr(self,"toc%s"%name)
1068 except:
1069 self._debug("no function for UID %s" % uid)
1070 return
1071 func(user,cookie,seq,pip,vip,port,tlvs)
1072
1073 def tocSEND_FILE(self,user,cookie,seq,pip,vip,port,tlvs):
1074 if tlvs.has_key('12'):
1075 description=tlvs['12']
1076 else:
1077 description=""
1078 subtype,numfiles,size=struct.unpack("!HHI",tlvs['10001'][:8])
1079 name=tlvs['10001'][8:-4]
1080 while name[-1]=='\000':
1081 name=name[:-1]
1082 self._cookies[cookie]=[user,SEND_FILE_UID,pip,port,{'name':name}]
1083 self.rvousProposal("send",cookie,user,vip,port,description=description,
1084 name=name,files=numfiles,size=size)
1085
1086 def tocGET_FILE(self,user,cookie,seq,pip,vip,port,tlvs):
1087 return
1088 # XXX add this back in
1089 #reactor.clientTCP(pip,port,GetFileTransfer(self,cookie,os.path.expandus er("~")))
1090 #self.rvous_accept(user,cookie,GET_FILE_UID)
1091
1092 def onLine(self):
1093 """
1094 called when we are first online
1095 """
1096 pass
1097
1098 def gotConfig(self,mode,buddylist,permit,deny):
1099 """
1100 called when we get a configuration from the server
1101 mode := permit/deny mode
1102 buddylist := current buddylist
1103 permit := permit list
1104 deny := deny list
1105 """
1106 pass
1107
1108 def hearError(self,code,args):
1109 """
1110 called when an error is received
1111 code := error code
1112 args := misc. arguments (username, etc.)
1113 """
1114 pass
1115
1116 def hearWarning(self,newamount,username):
1117 """
1118 called when we get warned
1119 newamount := the current warning level
1120 username := the user who warned us, or '' if it's anonymous
1121 """
1122 pass
1123
1124 def hearMessage(self,username,message,autoreply):
1125 """
1126 called when you receive an IM
1127 username := the user who the IM is from
1128 message := the message
1129 autoreply := true if the message is an autoreply from an away message
1130 """
1131 pass
1132
1133 def updateBuddy(self,username,online,evilness,signontime,idletime,userclass, away):
1134 """
1135 called when a buddy changes state
1136 username := the user whos state changed
1137 online := true if the user is online
1138 evilness := the users current warning level
1139 signontime := the time the user signed on (UNIX epoch)
1140 idletime := the time the user has been idle (minutes)
1141 away := true if the user is away
1142 userclass := the class of the user (generally " O")
1143 """
1144 pass
1145
1146 def chatJoined(self,roomid,roomname,users):
1147 """
1148 we just joined a chat room
1149 roomid := the AIM id for the room
1150 roomname := the name for the room
1151 users := a list of the users already in the room
1152 """
1153 pass
1154
1155 def chatUpdate(self,roomid,username,inroom):
1156 """
1157 a user has joined the room
1158 roomid := the AIM id for the room
1159 username := the username
1160 inroom := true if the user is in the room
1161 """
1162 pass
1163
1164 def chatHearMessage(self,roomid,username,message):
1165 """
1166 a message was sent to the room
1167 roomid := the AIM id for the room
1168 username := the user who sent the message
1169 message := the message
1170 """
1171 pass
1172
1173 def chatHearWhisper(self,roomid,username,message):
1174 """
1175 someone whispered to us in a chatroom
1176 roomid := the AIM for the room
1177 username := the user who whispered to us
1178 message := the message
1179 """
1180 pass
1181
1182 def chatInvited(self,roomid,roomname,username,message):
1183 """
1184 we were invited to a chat room
1185 roomid := the AIM id for the room
1186 roomname := the name of the room
1187 username := the user who invited us
1188 message := the invite message
1189 """
1190 pass
1191
1192 def chatLeft(self,roomid):
1193 """
1194 we left the room
1195 roomid := the AIM id for the room
1196 """
1197 pass
1198
1199 def rvousProposal(self,type,cookie,user,vip,port,**kw):
1200 """
1201 we were asked for a rondevouz
1202 type := the type of rondevous. currently, one of ["send"]
1203 cookie := the cookie. pass this to rvous_accept()
1204 user := the user who asked us
1205 vip := their verified_ip
1206 port := the port they want us to conenct to
1207 kw := misc. args
1208 """
1209 pass #self.rvous_accept(cookie)
1210
1211 def receiveBytes(self,user,file,chunk,sofar,total):
1212 """
1213 we received part of a file from a file transfer
1214 file := the name of the file
1215 chunk := the chunk of data
1216 sofar := how much data we've gotten so far
1217 total := the total amount of data
1218 """
1219 pass #print user,file,sofar,total
1220
1221 def isaway(self):
1222 """
1223 return our away status
1224 """
1225 return len(self._awaymessage)>0
1226
1227 def set_config(self,mode,buddylist,permit,deny):
1228 """
1229 set the server configuration
1230 mode := permit mode
1231 buddylist := buddy list
1232 permit := permit list
1233 deny := deny list
1234 """
1235 s="m %s\n"%mode
1236 for g in buddylist.keys():
1237 s=s+"g %s\n"%g
1238 for u in buddylist[g]:
1239 s=s+"b %s\n"%u
1240 for p in permit:
1241 s=s+"p %s\n"%p
1242 for d in deny:
1243 s=s+"d %s\n"%d
1244 #s="{\n"+s+"\n}"
1245 self.sendFlap(2,"toc_set_config %s"%quote(s))
1246
1247 def add_buddy(self,buddies):
1248 s=""
1249 if type(buddies)==type(""): buddies=[buddies]
1250 for b in buddies:
1251 s=s+" "+normalize(b)
1252 self.sendFlap(2,"toc_add_buddy%s"%s)
1253
1254 def del_buddy(self,buddies):
1255 s=""
1256 if type(buddies)==type(""): buddies=[buddies]
1257 for b in buddies:
1258 s=s+" "+b
1259 self.sendFlap(2,"toc_remove_buddy%s"%s)
1260
1261 def add_permit(self,users):
1262 if type(users)==type(""): users=[users]
1263 s=""
1264 if self._privacymode!=PERMITSOME:
1265 self._privacymode=PERMITSOME
1266 self._permitlist=[]
1267 for u in users:
1268 u=normalize(u)
1269 if u not in self._permitlist:self._permitlist.append(u)
1270 s=s+" "+u
1271 if not s:
1272 self._privacymode=DENYALL
1273 self._permitlist=[]
1274 self._denylist=[]
1275 self.sendFlap(2,"toc_add_permit"+s)
1276
1277 def del_permit(self,users):
1278 if type(users)==type(""): users=[users]
1279 p=self._permitlist[:]
1280 for u in users:
1281 u=normalize(u)
1282 if u in p:
1283 p.remove(u)
1284 self.add_permit([])
1285 self.add_permit(p)
1286
1287 def add_deny(self,users):
1288 if type(users)==type(""): users=[users]
1289 s=""
1290 if self._privacymode!=DENYSOME:
1291 self._privacymode=DENYSOME
1292 self._denylist=[]
1293 for u in users:
1294 u=normalize(u)
1295 if u not in self._denylist:self._denylist.append(u)
1296 s=s+" "+u
1297 if not s:
1298 self._privacymode=PERMITALL
1299 self._permitlist=[]
1300 self._denylist=[]
1301 self.sendFlap(2,"toc_add_deny"+s)
1302
1303 def del_deny(self,users):
1304 if type(users)==type(""): users=[users]
1305 d=self._denylist[:]
1306 for u in users:
1307 u=normalize(u)
1308 if u in d:
1309 d.remove(u)
1310 self.add_deny([])
1311 if d:
1312 self.add_deny(d)
1313
1314 def signon(self):
1315 """
1316 called to finish the setup, and signon to the network
1317 """
1318 self.sendFlap(2,"toc_init_done")
1319 self.sendFlap(2,"toc_set_caps %s" % (SEND_FILE_UID,)) # GET_FILE_UID)
1320
1321 def say(self,user,message,autoreply=0):
1322 """
1323 send a message
1324 user := the user to send to
1325 message := the message
1326 autoreply := true if the message is an autoreply (good for away messages )
1327 """
1328 if autoreply: a=" auto"
1329 else: a=''
1330 self.sendFlap(2,"toc_send_im %s %s%s"%(normalize(user),quote(message),a) )
1331
1332 def idle(self,idletime=0):
1333 """
1334 change idle state
1335 idletime := the seconds that the user has been away, or 0 if they're bac k
1336 """
1337 self.sendFlap(2,"toc_set_idle %s" % int(idletime))
1338
1339 def evil(self,user,anon=0):
1340 """
1341 warn a user
1342 user := the user to warn
1343 anon := if true, an anonymous warning
1344 """
1345 self.sendFlap(2,"toc_evil %s %s"%(normalize(user), (not anon and "anon") or "norm"))
1346
1347 def away(self,message=''):
1348 """
1349 change away state
1350 message := the message, or '' to come back from awayness
1351 """
1352 self._awaymessage=message
1353 if message:
1354 message=' '+quote(message)
1355 self.sendFlap(2,"toc_set_away%s"%message)
1356
1357 def chat_join(self,exchange,roomname):
1358 """
1359 join a chat room
1360 exchange := should almost always be 4
1361 roomname := room name
1362 """
1363 roomname=string.replace(roomname," ","")
1364 self.sendFlap(2,"toc_chat_join %s %s"%(int(exchange),roomname))
1365
1366 def chat_say(self,roomid,message):
1367 """
1368 send a message to a chatroom
1369 roomid := the AIM id for the room
1370 message := the message to send
1371 """
1372 self.sendFlap(2,"toc_chat_send %s %s"%(int(roomid),quote(message)))
1373
1374 def chat_whisper(self,roomid,user,message):
1375 """
1376 whisper to another user in a chatroom
1377 roomid := the AIM id for the room
1378 user := the user to whisper to
1379 message := the message to send
1380 """
1381 self.sendFlap(2,"toc_chat_whisper %s %s %s"%(int(roomid),normalize(user) ,quote(message)))
1382
1383 def chat_leave(self,roomid):
1384 """
1385 leave a chat room.
1386 roomid := the AIM id for the room
1387 """
1388 self.sendFlap(2,"toc_chat_leave %s" % int(roomid))
1389
1390 def chat_invite(self,roomid,usernames,message):
1391 """
1392 invite a user[s] to the chat room
1393 roomid := the AIM id for the room
1394 usernames := either a string (one username) or a list (more than one)
1395 message := the message to invite them with
1396 """
1397 if type(usernames)==type(""): # a string, one username
1398 users=usernames
1399 else:
1400 users=""
1401 for u in usernames:
1402 users=users+u+" "
1403 users=users[:-1]
1404 self.sendFlap(2,"toc_chat_invite %s %s %s" % (int(roomid),quote(message) ,users))
1405
1406 def chat_accept(self,roomid):
1407 """
1408 accept an invite to a chat room
1409 roomid := the AIM id for the room
1410 """
1411 self.sendFlap(2,"toc_chat_accept %s"%int(roomid))
1412
1413 def rvous_accept(self,cookie):
1414 user,uuid,pip,port,d=self._cookies[cookie]
1415 self.sendFlap(2,"toc_rvous_accept %s %s %s" % (normalize(user),
1416 cookie,uuid))
1417 if uuid==SEND_FILE_UID:
1418 protocol.ClientCreator(reactor, SendFileTransfer,self,cookie,user,d[ "name"]).connectTCP(pip,port)
1419
1420 def rvous_cancel(self,cookie):
1421 user,uuid,pip,port,d=self._cookies[cookie]
1422 self.sendFlap(2,"toc_rvous_accept %s %s %s" % (normalize(user),
1423 cookie,uuid))
1424 del self._cookies[cookie]
1425
1426
1427 class SendFileTransfer(protocol.Protocol):
1428 header_fmt="!4s2H8s6H10I32s3c69s16s2H64s"
1429
1430 def __init__(self,client,cookie,user,filename):
1431 self.client=client
1432 self.cookie=cookie
1433 self.user=user
1434 self.filename=filename
1435 self.hdr=[0,0,0]
1436 self.sofar=0
1437
1438 def dataReceived(self,data):
1439 if not self.hdr[2]==0x202:
1440 self.hdr=list(struct.unpack(self.header_fmt,data[:256]))
1441 self.hdr[2]=0x202
1442 self.hdr[3]=self.cookie
1443 self.hdr[4]=0
1444 self.hdr[5]=0
1445 self.transport.write(apply(struct.pack,[self.header_fmt]+self.hdr))
1446 data=data[256:]
1447 if self.hdr[6]==1:
1448 self.name=self.filename
1449 else:
1450 self.name=self.filename+self.hdr[-1]
1451 while self.name[-1]=="\000":
1452 self.name=self.name[:-1]
1453 if not data: return
1454 self.sofar=self.sofar+len(data)
1455 self.client.receiveBytes(self.user,self.name,data,self.sofar,self.hdr[11 ])
1456 if self.sofar==self.hdr[11]: # end of this file
1457 self.hdr[2]=0x204
1458 self.hdr[7]=self.hdr[7]-1
1459 self.hdr[9]=self.hdr[9]-1
1460 self.hdr[19]=DUMMY_CHECKSUM # XXX really calculate this
1461 self.hdr[18]=self.hdr[18]+1
1462 self.hdr[21]="\000"
1463 self.transport.write(apply(struct.pack,[self.header_fmt]+self.hdr))
1464 self.sofar=0
1465 if self.hdr[7]==0:
1466 self.transport.loseConnection()
1467
1468
1469 class GetFileTransfer(protocol.Protocol):
1470 header_fmt="!4s 2H 8s 6H 10I 32s 3c 69s 16s 2H 64s"
1471 def __init__(self,client,cookie,dir):
1472 self.client=client
1473 self.cookie=cookie
1474 self.dir=dir
1475 self.buf=""
1476
1477 def connectionMade(self):
1478 def func(f,path,names):
1479 names.sort(lambda x,y:cmp(string.lower(x),string.lower(y)))
1480 for n in names:
1481 name=os.path.join(path,n)
1482 lt=time.localtime(os.path.getmtime(name))
1483 size=os.path.getsize(name)
1484 f[1]=f[1]+size
1485 f.append("%02d/%02d/%4d %02d:%02d %8d %s" %
1486 (lt[1],lt[2],lt[0],lt[3],lt[4],size,name[f[0]:]))
1487 f=[len(self.dir)+1,0]
1488 os.path.walk(self.dir,func,f)
1489 size=f[1]
1490 self.listing=string.join(f[2:],"\r\n")+"\r\n"
1491 open("\\listing.txt","w").write(self.listing)
1492 hdr=["OFT2",256,0x1108,self.cookie,0,0,len(f)-2,len(f)-2,1,1,size,
1493 len(self.listing),os.path.getmtime(self.dir),
1494 checksum(self.listing),0,0,0,0,0,0,"OFT_Windows ICBMFT V1.1 32",
1495 "\002",chr(0x1a),chr(0x10),"","",0,0,""]
1496 self.transport.write(apply(struct.pack,[self.header_fmt]+hdr))
1497
1498 def dataReceived(self,data):
1499 self.buf=self.buf+data
1500 while len(self.buf)>=256:
1501 hdr=list(struct.unpack(self.header_fmt,self.buf[:256]))
1502 self.buf=self.buf[256:]
1503 if hdr[2]==0x1209:
1504 self.file=StringIO.StringIO(self.listing)
1505 self.transport.registerProducer(self,0)
1506 elif hdr[2]==0x120b: pass
1507 elif hdr[2]==0x120c: # file request
1508 file=hdr[-1]
1509 for k,v in [["\000",""],["\001",os.sep]]:
1510 file=string.replace(file,k,v)
1511 self.name=os.path.join(self.dir,file)
1512 self.file=open(self.name,'rb')
1513 hdr[2]=0x0101
1514 hdr[6]=hdr[7]=1
1515 hdr[10]=hdr[11]=os.path.getsize(self.name)
1516 hdr[12]=os.path.getmtime(self.name)
1517 hdr[13]=checksum_file(self.file)
1518 self.file.seek(0)
1519 hdr[18]=hdr[19]=0
1520 hdr[21]=chr(0x20)
1521 self.transport.write(apply(struct.pack,[self.header_fmt]+hdr))
1522 log.msg("got file request for %s"%file,hex(hdr[13]))
1523 elif hdr[2]==0x0202:
1524 log.msg("sending file")
1525 self.transport.registerProducer(self,0)
1526 elif hdr[2]==0x0204:
1527 log.msg("real checksum: %s"%hex(hdr[19]))
1528 del self.file
1529 elif hdr[2]==0x0205: # resume
1530 already=hdr[18]
1531 if already:
1532 data=self.file.read(already)
1533 else:
1534 data=""
1535 log.msg("restarting at %s"%already)
1536 hdr[2]=0x0106
1537 hdr[19]=checksum(data)
1538 self.transport.write(apply(struct.pack,[self.header_fmt]+hdr))
1539 elif hdr[2]==0x0207:
1540 self.transport.registerProducer(self,0)
1541 else:
1542 log.msg("don't understand 0x%04x"%hdr[2])
1543 log.msg(hdr)
1544
1545 def resumeProducing(self):
1546 data=self.file.read(4096)
1547 log.msg(len(data))
1548 if not data:
1549 self.transport.unregisterProducer()
1550 self.transport.write(data)
1551
1552 def pauseProducing(self): pass
1553
1554 def stopProducing(self): del self.file
1555
1556 # UUIDs
1557 SEND_FILE_UID = "09461343-4C7F-11D1-8222-444553540000"
1558 GET_FILE_UID = "09461348-4C7F-11D1-8222-444553540000"
1559 UUIDS={
1560 SEND_FILE_UID:"SEND_FILE",
1561 GET_FILE_UID:"GET_FILE"
1562 }
1563
1564 # ERRORS
1565 # general
1566 NOT_AVAILABLE=901
1567 CANT_WARN=902
1568 MESSAGES_TOO_FAST=903
1569 # admin
1570 BAD_INPUT=911
1571 BAD_ACCOUNT=912
1572 REQUEST_ERROR=913
1573 SERVICE_UNAVAILABLE=914
1574 # chat
1575 NO_CHAT_IN=950
1576 # im and info
1577 SEND_TOO_FAST=960
1578 MISSED_BIG_IM=961
1579 MISSED_FAST_IM=962
1580 # directory
1581 DIR_FAILURE=970
1582 TOO_MANY_MATCHES=971
1583 NEED_MORE_QUALIFIERS=972
1584 DIR_UNAVAILABLE=973
1585 NO_EMAIL_LOOKUP=974
1586 KEYWORD_IGNORED=975
1587 NO_KEYWORDS=976
1588 BAD_LANGUAGE=977
1589 BAD_COUNTRY=978
1590 DIR_FAIL_UNKNOWN=979
1591 # authorization
1592 BAD_NICKNAME=980
1593 SERVICE_TEMP_UNAVAILABLE=981
1594 WARNING_TOO_HIGH=982
1595 CONNECTING_TOO_QUICK=983
1596 UNKNOWN_SIGNON=989
1597
1598 STD_MESSAGE={}
1599 STD_MESSAGE[NOT_AVAILABLE]="%s not currently available"
1600 STD_MESSAGE[CANT_WARN]="Warning of %s not currently available"
1601 STD_MESSAGE[MESSAGES_TOO_FAST]="A message has been dropped, you are exceeding th e server speed limit"
1602 STD_MESSAGE[BAD_INPUT]="Error validating input"
1603 STD_MESSAGE[BAD_ACCOUNT]="Invalid account"
1604 STD_MESSAGE[REQUEST_ERROR]="Error encountered while processing request"
1605 STD_MESSAGE[SERVICE_UNAVAILABLE]="Service unavailable"
1606 STD_MESSAGE[NO_CHAT_IN]="Chat in %s is unavailable"
1607 STD_MESSAGE[SEND_TOO_FAST]="You are sending messages too fast to %s"
1608 STD_MESSAGE[MISSED_BIG_IM]="You missed an IM from %s because it was too big"
1609 STD_MESSAGE[MISSED_FAST_IM]="You missed an IM from %s because it was sent too fa st"
1610 # skipping directory for now
1611 STD_MESSAGE[BAD_NICKNAME]="Incorrect nickname or password"
1612 STD_MESSAGE[SERVICE_TEMP_UNAVAILABLE]="The service is temporarily unavailable"
1613 STD_MESSAGE[WARNING_TOO_HIGH]="Your warning level is currently too high to sign on"
1614 STD_MESSAGE[CONNECTING_TOO_QUICK]="You have been connecting and disconnecting to o frequently. Wait 10 minutes and try again. If you continue to try, you will need to wait even longer."
1615 STD_MESSAGE[UNKNOWN_SIGNON]="An unknown signon error has occurred %s"
OLDNEW
« no previous file with comments | « third_party/twisted_8_1/twisted/words/protocols/oscar.py ('k') | third_party/twisted_8_1/twisted/words/scripts/__init__.py » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698