Subversion Repositories Kolibri OS

Rev

Rev 3212 | Go to most recent revision | Details | Compare with Previous | Last modification | View Log | RSS feed

Rev Author Line No. Line
3191 hidnplayr 1
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
2
;;                                                                 ;;
3
;; Copyright (C) KolibriOS team 2004-2013. All rights reserved.    ;;
4
;; Distributed under terms of the GNU General Public License       ;;
5
;;                                                                 ;;
6
;;                                                                 ;;
7
;;         GNU GENERAL PUBLIC LICENSE                              ;;
8
;;          Version 2, June 1991                                   ;;
9
;;                                                                 ;;
10
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
11
 
12
 
13
server_parser:
14
 
15
        mov     esi, servercommand
16
 
17
        cmp     byte [esi], ':'
18
        jne     .parse
19
 
20
  .spaceloop:
21
        lodsb
22
        test    al, al
23
        jz      .fail
24
        cmp     al, ' '
25
        jne     .spaceloop
26
 
27
  .parse:
28
        mov     eax, [esi]
29
        or      eax, 0x20202020
30
        mov     edi, server_commands
31
        mov     ecx, server_commands.number
32
 
33
  .loop:
34
        scasd
35
        je      .got_cmd
36
        add     edi, 4
37
        dec     ecx
38
        jnz     .loop
39
 
40
  .fail:
41
        ret
42
 
43
  .got_cmd:
3214 hidnplayr 44
        jmp     dword[edi]
3191 hidnplayr 45
 
46
 
47
server_commands:
48
 
49
        dd      '328 ', cmd_328
50
        dd      '332 ', cmd_topic
51
        dd      '333 ', cmd_333         ; nickname and time of topic
52
        dd      '353 ', cmd_353         ; name reply
53
        dd      '366 ', cmd_366         ; end of names list
54
        dd      '372 ', cmd_372         ; motd
55
        dd      '375 ', cmd_375         ; start of motd
56
        dd      '376 ', cmd_376         ; end of motd
57
        dd      '421 ', cmd_421         ; unknown command
58
        dd      'join', cmd_join
59
        dd      'kick', cmd_kick
60
        dd      'mode', cmd_mode
61
        dd      'nick', cmd_nick
62
        dd      'part', cmd_part
63
        dd      'ping', cmd_ping
64
        dd      'priv', cmd_privmsg
65
        dd      'quit', cmd_quit
66
        dd      'noti', cmd_notice
67
 
68
        .number = ($ - server_commands) / 8
69
 
70
compare_to_nick:
71
 
72
        push    esi
73
        mov     ecx, MAX_NICK_LEN
74
        mov     esi, user_nick
75
  .loop:
76
        lodsb
77
        cmp     al, ' '
78
        jbe     .done
79
        cmp     al, 'a'
80
        jb      .ok
81
        cmp     al, 'z'
82
        ja      .ok
83
        sub     al, 0x20
84
  .ok:
85
 
86
        mov     bl, byte[edi]
87
        cmp     bl, 'a'
88
        jb      .ok2
89
        cmp     bl, 'z'
90
        ja      .ok2
91
        sub     bl, 0x20
92
  .ok2:
93
        cmp     bl, al
94
        jne     .not_equal
95
        inc     edi
96
        dec     ecx
97
        jnz     .loop
98
 
99
  .done:
100
        xor     eax, eax
101
        pop     esi
102
        ret
103
 
104
  .not_equal:
105
        or      eax, -1
106
        pop     esi
107
        ret
108
 
109
 
110
 
111
find_window:
112
 
113
;        mov     [window_print],
114
 
115
        ret
116
 
117
 
118
 
119
cmd_328:
120
cmd_421:
121
cmd_372:
122
cmd_375:
123
cmd_376:
124
        add     esi, 4
125
        jmp     cmd_notice.loop
126
 
127
cmd_notice:
128
 
129
        cmp     byte[servercommand], ':'
130
        jne     .gogogo
131
 
132
        mov     byte [esi-1], 0
133
        push    esi
134
        mov     esi, str_1
135
        call    print_text2
136
        mov     esi, servercommand+1
137
        call    print_text2
138
        mov     esi, str_2
139
        call    print_text2
140
        pop     esi
141
 
142
  .gogogo:
143
        add     esi, 6
144
 
145
  .loop:
146
        inc     esi
147
        cmp     byte [esi], 0
148
        je      .fail
3212 hidnplayr 149
;        cmp     byte [esi], 10  ; newline
150
;        je      server_parser.parse
3191 hidnplayr 151
        cmp     byte [esi], ' '
152
        jne     .loop
153
 
154
  .loop2:
155
        inc     esi
156
        cmp     byte [esi], 0
157
        je      .fail
158
        cmp     byte [esi], ' '
159
        je      .loop2
160
        cmp     byte [esi], ':'
161
        je      .loop2
162
 
163
        call    print_text2
164
        mov     esi, str_newline
165
        call    print_text2
166
 
167
  .fail:
168
 
169
        ret
170
 
171
 
172
 
173
cmd_ping:
174
 
175
; Just change PING to PONG
176
        mov     dword[esi], 'PONG'
177
 
178
; Find the end of the command
179
        lea     edi, [esi + 5]
180
        xor     al, al
181
        repne   scasb
182
 
183
; Now send it back
184
        mov     edx, esi
185
        mov     esi, edi
186
        mov     word [esi], 0x0d0a
187
        inc     esi
188
        inc     esi
189
        sub     esi, edx
190
        mcall   send, [socketnum], , , 0
191
 
192
        ret
193
 
194
 
195
 
196
cmd_privmsg:
197
 
3214 hidnplayr 198
        add     esi, 8  ; skip 'PRIVMSG '
199
 
3191 hidnplayr 200
; Check if it was destined for me privately
201
        mov     edi, servercommand+1
202
        call    compare_to_nick
203
;;;        je      .private
204
 
205
; If not, find the correct window ???
206
 
207
; now find the end of nick
208
        mov     edi, esi
209
  .loop:
210
        inc     edi
211
        cmp     byte [edi], 0
212
        je      .fail
213
        cmp     byte [edi], ' '
214
        jne     .loop
215
 
216
  .loop2:
217
        inc     edi
218
        cmp     byte [edi], 0
219
        je      .fail
220
        cmp     byte [edi], ' '
221
        je      .loop2
222
        cmp     byte [edi], ':'
223
        je      .loop2
224
        cmp     byte [edi], 1
225
        je      cmd_ctcp
226
 
227
; Action?
228
        cmp     dword[edi+1], 'ACTI'
229
        je      .action
230
 
231
; nope, just plain old privmsg
232
if TIMESTAMP
233
        call    print_timestamp
234
end if
235
 
236
        push    edi
237
        mov     bl, '<'
238
        call    print_character
239
 
240
        mov     eax, servercommand+1
241
        mov     dl, '!'
242
        call    print_text
243
 
244
        mov     bl, '>'
245
        call    print_character
246
 
247
        mov     bl, ' '
248
        call    print_character
249
 
250
        pop     esi
251
        call    print_text2
252
 
253
        mov     bl, 10
254
        call    print_character
255
 
256
  .fail:
257
        ret
258
 
259
  .action:
260
        push    edi
261
        if TIMESTAMP
262
        call    print_timestamp
263
        end if
264
 
265
        mov     esi, action_header_short
266
        call    print_text2
267
 
268
        mov     eax, servercommand+1
269
        mov     dl, ' '
270
        call    print_text
271
 
272
        mov     bl, ' '
273
        call    print_character
274
 
275
        pop     esi
276
        add     esi, 8
277
        call    print_text2
278
 
279
        mov     bl, 10
280
        call    print_character
281
 
282
        ret
283
 
284
cmd_ctcp:
285
 
286
        cmp     dword[edi+1], 'VERS'
287
        je      .version
288
 
289
        cmp     dword[edi+1], 'TIME'
290
        je      .time
291
 
292
        cmp     dword[edi+1], 'PING'
293
        je      .ping
294
 
295
        ret
296
 
297
  .time:
298
        lea     esi, [edi+1]
299
        mov     byte [edi+5], ' '
300
        add     edi, 6
301
 
302
        ; TODO: add system date (fn 29) in human readable format
303
 
304
        mcall   3                       ; get system time
305
 
306
        mov     ecx, 3
307
  .timeloop:
308
        mov     bl, al
309
        shr     al, 4
310
        add     al, '0'
311
        stosb
312
 
313
        mov     al, bl
314
        and     al, 0x0f
315
        add     al, '0'
316
        stosb
317
 
318
        dec     ecx
319
        jz      .timedone
320
 
321
        mov     al, ':'
322
        stosb
323
        shr     eax, 8
324
        jmp     .timeloop
325
 
326
  .timedone:
327
        xor     al, al
328
        stosb
329
        call    ctcp_reply
330
 
331
        if TIMESTAMP
332
        call    print_timestamp
333
        end if
334
 
335
        mov     esi, ctcp_header
336
        call    print_text2
337
 
338
        mov     esi, servercommand+1
339
        call    print_text2
340
 
341
        mov     esi, ctcp_time
342
        call    print_text2
343
 
344
        ret
345
 
346
  .version:
347
        mov     esi, str_version
348
        call    ctcp_reply
349
 
350
        if TIMESTAMP
351
        call    print_timestamp
352
        end if
353
 
354
        mov     esi, ctcp_header
355
        call    print_text2
356
 
357
        mov     esi, servercommand+1
358
        call    print_text2
359
 
360
        mov     esi, ctcp_version
361
        call    print_text2
362
 
363
        ret
364
 
365
  .ping:
366
        lea     esi, [edi+1]
367
        call    ctcp_reply
368
 
369
        if TIMESTAMP
370
        call    print_timestamp
371
        end if
372
 
373
        mov     esi, ctcp_header
374
        call    print_text2
375
 
376
        mov     esi, servercommand+1
377
        call    print_text2
378
 
379
        mov     esi, ctcp_ping
380
        call    print_text2
381
 
382
        ret
383
 
384
 
385
 
386
ctcp_reply:
387
 
388
        push    esi
389
 
390
        mov     dword [usercommand], 'NOTI'
391
        mov     dword [usercommand+4], 'CE  '
392
 
393
        mov     esi, servercommand+1
394
        mov     edi, usercommand+7
395
  .nickloop:
396
        lodsb
397
        cmp     al, '!'
398
        je      .done
399
        cmp     al, ' '
400
        je      .done
401
        test    al, al
402
        je      .fail
403
        stosb
404
        jmp     .nickloop
405
  .done:
406
        mov     byte [esi-1], 0
407
        mov     ax, ' :'
408
        stosw
409
        mov     al, 1
410
        stosb
411
 
412
        pop     esi
413
  .replyloop:
414
        lodsb
415
        cmp     al, 1
416
        jbe     .done2
417
        stosb
418
        jmp     .replyloop
419
  .done2:
420
 
421
        mov     al, 1
422
        stosb
423
        mov     ax, 0x0a0d
424
        stosw
425
 
426
        lea     esi, [edi - usercommand]
427
        mcall   send, [socketnum], usercommand, , 0
428
  .fail:
429
        ret
430
 
431
 
432
 
433
cmd_part:
434
 
435
; Is it me who parted?
436
        mov     edi, servercommand+1
437
        call    compare_to_nick
438
        jne     .dont_close
439
 
440
; yes, close the window
441
        mov     edi, [window_print]
442
        mov     [edi + window.flags], FLAG_UPDATED + FLAG_CLOSE
443
 
444
        ret
445
 
446
; somebody else parted, just print message
447
  .dont_close:
448
        push    esi
449
        mov     esi, action_header
450
        call    print_text2
451
 
452
        mov     eax, servercommand+1
453
        mov     dl, '!'
454
        mov     cl, ' '
455
        call    print_text
456
 
457
        mov     esi, has_left_channel
458
        call    print_text2
459
 
460
        pop     esi
461
        call    print_text2
462
 
463
        ret
464
 
465
 
466
 
467
cmd_join:
468
; compare nick: did we join a channel?
469
        mov     edi, servercommand+1
470
        call    compare_to_nick
471
        jne     .no_new_window
472
 
473
; create channel window - search for empty slot
474
        mov     ebx, windows
475
        mov     ecx, MAX_WINDOWS
476
  .loop:
477
        cmp     [ebx + window.data_ptr], 0
478
        je      .free_found
479
        add     ebx, sizeof.window
480
        dec     ecx
481
        jnz     .loop
482
; Error: no more available windows!! ;;;;; TODO
483
  .fail:
484
        ret
485
 
486
  .free_found:
487
        push    ebx
488
        call    window_create
489
        pop     ebx
490
        test    eax, eax
491
        jz      .fail
492
        mov     [ebx + window.data_ptr], eax
493
        mov     [ebx + window.type], WINDOWTYPE_CHANNEL
494
        mov     [ebx + window.flags], 0
3214 hidnplayr 495
 
496
        add     esi, 5  ; skip 'JOIN '  ; FIXME: perhaps scan for spaces instead?
3191 hidnplayr 497
        call    window_set_name
498
 
499
        mov     [window_open], ebx
500
        mov     [window_print], ebx
501
        call    window_refresh
502
 
503
        push    esi
504
        mov     esi, action_header
505
        call    print_text2
506
 
507
        mov     esi, str_talking
508
        call    print_text2
509
 
510
        pop     eax
511
        mov     dl, ' '
512
        call    print_text
513
 
514
        mov     esi, str_dotnewline
515
        call    print_text2
516
 
517
        call    draw_window
518
 
519
        ret
520
 
521
  .no_new_window:
522
        push    esi
523
        call    window_set_name
524
 
525
        mov     esi, action_header
526
        call    print_text2
527
 
528
        mov     eax, servercommand+1
529
        mov     dl, ' '
530
        call    print_text
531
 
532
        mov     esi, joins_channel
533
        call    print_text2
534
 
535
        pop     esi
536
        call    print_text2
537
 
538
        mov     esi, str_newline
539
        call    print_text2
540
 
541
        ret
542
 
543
 
544
 
545
 
546
cmd_nick:       ; FIXME
547
 
548
        push    esi
549
; test for change of my nick
550
        mov     esi, servercommand+1
551
        mov     edi, user_nick
552
        mov     ecx, MAX_NICK_LEN
553
        rep     cmpsb
554
        cmp     byte[edi-1], 0
555
        jne     .notmy
556
        cmp     byte[esi-1], '!'
557
        jne     .notmy
558
 
559
; yes, this is my nick, set to new
560
        pop     esi
561
        or      ecx, -1
562
        mov     edi, esi
563
        xor     eax, eax
564
        repne   scasb
565
        neg     ecx
566
        cmp     ecx, MAX_NICK_LEN
567
        jb      @f
568
        mov     ecx, MAX_NICK_LEN
569
      @@:
570
        mov     edi, user_nick
571
        rep     movsb
572
  .notmy:
573
 
574
; replace nick in all lists of users
575
        mov     ebx, windows
576
  .channels:
577
        mov     esi, [ebx + window.data_ptr]
578
        lea     esi, [esi + window_data.names]
579
;;;;;        mov     edx, [esi + window_data.nameslen]
580
        add     edx, esi
581
  .nicks:
582
        mov     edi, servercommand+1
583
        cmp     byte[esi], '@'
584
        jne     @f
585
        inc     esi
586
 
587
  @@:
588
        cmp     esi, edx
589
        jae     .srcdone
590
        lodsb
591
        cmp     al, ' '
592
        je      .srcdone
593
        scasb
594
        je      @b
595
 
596
  @@:
597
        cmp     esi, edx
598
        jae     .nextchannel
599
        lodsb
600
        cmp     al, ' '
601
        jne     @b
602
 
603
  .nextnick:
604
        cmp     esi, edx
605
        jae     .nextchannel
606
        lodsb
607
        cmp     al, ' '
608
        jz      .nextnick
609
        dec     esi
610
        jmp     .nicks
611
 
612
 
613
  .srcdone:
614
        cmp     byte [edi], '!'
615
        jne     .nextnick
616
 
617
; here we have esi -> end of nick which must be replaced to [servercommand_position]+6
618
        lea     edx, [edi-servercommand-1]
619
        sub     esi, edx
620
        or      ecx, -1
621
        xor     eax, eax
622
;        mov     edi, [servercommand_position]        ;;;;; FIXME
623
        repnz   scasb
624
        not     ecx
625
        dec     ecx
626
        push    ecx
627
        cmp     ecx, edx
628
        jb      .decrease
629
        jz      .copy
630
  .increase:
631
 
632
; new nick is longer than the old
633
        push    esi
634
        lea     edi, [ebx+120*10] ;;;;;;
635
        lea     esi, [edi+edx]
636
        sub     esi, ecx
637
        mov     ecx, esi
638
        sub     ecx, [esp]
639
        dec     esi
640
        dec     edi
641
        std
642
        rep     movsb
643
        cld
644
        pop     esi
645
        jmp     .copy
646
  .decrease:
647
; new nick is shorter than the old
648
        push    esi
649
        lea     edi, [esi+ecx]
650
        add     esi, edx
651
        lea     ecx, [ebx+120*10]
652
        sub     ecx, edi
653
        rep     movsb
654
        pop     esi
655
  .copy:
656
; copy nick
657
        mov     edi, esi
658
        dec     edi
659
;        mov     esi, [servercommand_position]        ;;;;; FIXME
660
        pop     ecx
661
        sub     edx, ecx
662
        sub     [ebx-4], edx
663
        rep     movsb
664
        mov     al, ' '
665
        stosb
666
 
667
  .nextchannel:
668
        add     ebx, sizeof.window
669
        cmp     ebx, windows + sizeof.window*MAX_WINDOWS
670
        jb      .channels
671
 
672
;        mov  [text_start], window_text + 120*80
673
 new_all_channels3:
674
 
675
        mov     esi, action_header_short
676
        call    print_text2
677
 
678
        mov     eax, servercommand+1
679
        mov     dl,'!'
680
        call    print_text
681
 
682
        mov     esi,is_now_known_as
683
        call    print_text2
684
 
685
;       mov     esi,[servercommand_position]        ;;;;; FIXME
686
        call    print_text2
687
 
688
;;;        call    notify_channel_thread
689
 
690
; go to next window (and check if its a channel!)
691
 
692
;        add     [text_start], 120*80
693
;        cmp     [text_start], I_END+120*80*20
694
;        jb      new_all_channels3
695
 
696
        ret
697
 
698
 
699
 
700
 
701
cmd_kick:
702
; Is it me who got kicked?
703
        mov     edi, servercommand+1
704
        call    compare_to_nick
705
        jne     .not_me
706
 
707
; TODO: mark channel as disconnected
708
 
709
  .not_me:
710
; find the channel user has been kicked from
711
        push    esi
712
        mov     esi, action_header_short
713
        call    print_text2
714
 
715
        mov     eax, servercommand+1
716
        mov     dl,'!'
717
        call    print_text
718
 
719
        mov     esi, kicked
720
        call    print_text2
721
 
722
        pop     esi
723
        call    print_text2
724
 
725
        ret
726
 
727
 
728
 
729
cmd_quit:
730
 
731
        mov     esi, action_header
732
        call    print_text2
733
 
734
        mov     eax, servercommand+1
735
        mov     dl, '!'
736
        call    print_text
737
 
738
        mov     esi, has_quit_irc
739
        call    print_text2
740
 
741
        ret
742
 
743
 
744
 
745
cmd_mode:
746
 
747
        push    esi
748
        mov     esi, action_header_short
749
        call    print_text2
750
 
751
        mov     eax, servercommand+1
752
        mov     dl, ' '
753
        call    print_text
754
 
755
        mov     esi, sets_mode
756
        call    print_text2
757
 
758
        pop     esi
759
        call    print_text2
760
 
761
        mov     esi, str_newline
762
        call    print_text2
763
 
764
        ret
765
 
766
 
767
cmd_353:        ; channel usernames reply
768
 
769
; TODO: mark a bit that we are receiving names
770
 
771
; first, find the channel name
772
  .loop1:
773
        lodsb
774
        cmp     al, '#'
775
        je      .got_channel
776
        test    al, al
777
        jnz     .loop1
778
 
779
        ret
780
 
781
  .got_channel:
782
;        call    find_channel   ;;;; ASSUME current channel for now
783
        mov     ebx, [window_print]
784
        mov     ebx, [ebx + window.data_ptr]
785
        lea     edi, [ebx + window_data.names]
786
        lea     edx, [edi + MAX_NICK_LEN]
787
 
788
; now find the semicolon separating channelname and usernames
789
  .loop2:
790
        lodsb
791
        cmp     al, ':'
792
        je      .namesloop
793
        test    al, al
794
        jnz     .loop2
795
 
796
        ret
797
 
798
  .namesloop:
799
; now the names list begins, separated with spaces
800
        lodsb
801
        test    al, al
802
        jz      .done
803
        cmp     al, ' '
804
        jz      .next
805
        stosb
806
        jmp     .namesloop
807
 
808
  .next:
809
        mov     edi, edx
810
        add     edx, MAX_NICK_LEN
811
 
812
;;;        cmp     edi, ..      ; Check for buffer overflow
813
        jmp     .namesloop
814
 
815
  .done:
816
        call    print_channel_list
817
 
818
        ret
819
 
820
 
821
 
822
 
823
cmd_366:        ; channel usernames end
824
 
825
; TODO: clear the bit that we are receiving names
826
 
827
 
828
        ret
829
 
830
 
831
cmd_topic:
832
 
833
  .loop:
834
        lodsb
835
        test    al, al
836
        je      .fail
837
        cmp     al, ':'
838
        jne     .loop
839
 
840
        push    esi
841
        mov     esi, action_header
842
        call    print_text2
843
 
844
        mov     esi, str_topic
845
        call    print_text2
846
 
847
        pop     esi
848
        call    print_text2
849
 
850
        mov     esi, str_newline
851
        call    print_text2
852
 
853
  .fail:
854
        ret
855
 
856
 
857
cmd_333:
858
 
859
; TODO: check channelname and change pointer accordingly
860
 
861
        mov     ecx, 3  ; number of spaces to find
862
  .loop:
863
        lodsb
864
        test    al, al
865
        je      .fail
866
        cmp     al, ' '
867
        jne     .loop
868
        dec     ecx
869
        jnz     .loop   ; find some more spaces
870
 
871
        push    esi
872
        mov     esi, action_header
873
        call    print_text2
874
 
875
        mov     esi, str_setby
876
        call    print_text2
877
 
878
        pop     esi
879
        call    print_text2
880
 
881
        mov     esi, str_newline
882
        call    print_text2
883
 
884
  .fail:
885
        ret
886