Mercurial > pidgin.yaz
comparison src/protocols/irc/irc.c @ 2687:2d544f48146d
[gaim-migrate @ 2700]
Anyone up for some fun!
committer: Tailor Script <tailor@pidgin.im>
author | Eric Warmenhoven <eric@warmenhoven.org> |
---|---|
date | Wed, 07 Nov 2001 11:14:33 +0000 |
parents | 37d80035e77f |
children | f3c094e78609 |
comparison
equal
deleted
inserted
replaced
2686:7b21c5446baf | 2687:2d544f48146d |
---|---|
49 | 49 |
50 struct irc_data { | 50 struct irc_data { |
51 int fd; | 51 int fd; |
52 gboolean online; | 52 gboolean online; |
53 guint32 timer; | 53 guint32 timer; |
54 | |
55 char *rxqueue; | |
56 int rxlen; | |
54 | 57 |
55 GString *str; | 58 GString *str; |
56 int bc; | 59 int bc; |
57 | 60 |
58 char *chantypes; | 61 char *chantypes; |
773 g_free(tmp); | 776 g_free(tmp); |
774 } | 777 } |
775 /* XXX should probably write_to_conv or something here */ | 778 /* XXX should probably write_to_conv or something here */ |
776 } | 779 } |
777 | 780 |
778 static void irc_callback(gpointer data, gint source, GaimInputCondition condition) | 781 static gboolean irc_parse(struct gaim_connection *gc, char *buf) |
779 { | 782 { |
780 struct gaim_connection *gc = data; | |
781 struct irc_data *idata = gc->proto_data; | 783 struct irc_data *idata = gc->proto_data; |
782 int i = 0; | |
783 gchar d[IRC_BUF_LEN], *buf = d; | |
784 gchar outbuf[IRC_BUF_LEN]; | 784 gchar outbuf[IRC_BUF_LEN]; |
785 char *word[PDIWORDS], *word_eol[PDIWORDS]; | 785 char *word[PDIWORDS], *word_eol[PDIWORDS]; |
786 char pdibuf[522]; | 786 char pdibuf[522]; |
787 char *ex, ip[128], nick[128]; | 787 char *ex, ip[128], nick[128]; |
788 char *cmd; | 788 char *cmd; |
789 | 789 |
790 if (!idata->online) { | |
791 /* Now lets sign ourselves on */ | |
792 account_online(gc); | |
793 serv_finish_login(gc); | |
794 | |
795 if (bud_list_cache_exists(gc)) | |
796 do_import(gc, NULL); | |
797 | |
798 /* we don't call this now because otherwise some IRC servers might not like us */ | |
799 idata->timer = g_timeout_add(20000, irc_request_buddy_update, gc); | |
800 idata->online = TRUE; | |
801 } | |
802 | |
803 do { | |
804 if (read(idata->fd, buf + i, 1) <= 0) { | |
805 hide_login_progress(gc, "Read error"); | |
806 signoff(gc); | |
807 return; | |
808 } | |
809 } while (buf[i++] != '\n'); | |
810 | |
811 buf[--i] = '\0'; | |
812 g_strchomp(buf); | |
813 debug_printf("IRC S: %s\n", buf); | |
814 | |
815 /* Check for errors */ | 790 /* Check for errors */ |
816 | 791 |
817 if (*buf != ':') { | 792 if (*buf != ':') { |
818 if (!strncmp(buf, "NOTICE ", 7)) | 793 if (!strncmp(buf, "NOTICE ", 7)) |
819 buf += 7; | 794 buf += 7; |
820 if (!strncmp(buf, "PING ", 5)) { | 795 if (!strncmp(buf, "PING ", 5)) { |
796 int r = FALSE; | |
821 g_snprintf(outbuf, sizeof(outbuf), "PONG %s\r\n", buf + 5); | 797 g_snprintf(outbuf, sizeof(outbuf), "PONG %s\r\n", buf + 5); |
822 if (irc_write(idata->fd, outbuf, strlen(outbuf)) < 0) { | 798 if (irc_write(idata->fd, outbuf, strlen(outbuf)) < 0) { |
823 hide_login_progress(gc, _("Unable to write")); | 799 hide_login_progress(gc, _("Unable to write")); |
824 signoff(gc); | 800 signoff(gc); |
801 r = TRUE; | |
825 } | 802 } |
826 return; | 803 return r; |
827 } | 804 } |
828 /* XXX doesn't handle ERROR */ | 805 /* XXX doesn't handle ERROR */ |
829 return; | 806 return FALSE; |
830 } | 807 } |
831 | 808 |
832 buf++; | 809 buf++; |
833 | 810 |
834 process_data_init(pdibuf, buf, word, word_eol, FALSE); | 811 process_data_init(pdibuf, buf, word, word_eol, FALSE); |
835 | 812 |
836 if (atoi(word[2])) { | 813 if (atoi(word[2])) { |
837 if (*word_eol[3]) | 814 if (*word_eol[3]) |
838 process_numeric(gc, word, word_eol); | 815 process_numeric(gc, word, word_eol); |
839 return; | 816 return FALSE; |
840 } | 817 } |
841 | 818 |
842 cmd = word[2]; | 819 cmd = word[2]; |
843 | 820 |
844 ex = strchr(pdibuf, '!'); | 821 ex = strchr(pdibuf, '!'); |
854 nick[sizeof(nick)-1] = 0; | 831 nick[sizeof(nick)-1] = 0; |
855 if ((ex - pdibuf) < sizeof (nick)) | 832 if ((ex - pdibuf) < sizeof (nick)) |
856 nick[ex - pdibuf] = 0; /* cut the buffer at the '!' */ | 833 nick[ex - pdibuf] = 0; /* cut the buffer at the '!' */ |
857 } | 834 } |
858 | 835 |
859 if (!strcmp(cmd, "INVITE")) { /* */ | 836 if (!strcmp(cmd, "INVITE")) { /* */ |
860 } else if (!strcmp(cmd, "JOIN")) { | 837 } else if (!strcmp(cmd, "JOIN")) { |
861 char *chan = *word[3] == ':' ? word[3] + 1 : word[3]; | 838 char *chan = *word[3] == ':' ? word[3] + 1 : word[3]; |
862 if (!g_strcasecmp(gc->displayname, nick)) { | 839 if (!g_strcasecmp(gc->displayname, nick)) { |
863 static int id = 1; | 840 static int id = 1; |
864 serv_got_joined_chat(gc, id++, chan); | 841 serv_got_joined_chat(gc, id++, chan); |
869 } | 846 } |
870 } else if (!strcmp(cmd, "KICK")) { | 847 } else if (!strcmp(cmd, "KICK")) { |
871 if (!strcmp(gc->displayname, word[4])) { | 848 if (!strcmp(gc->displayname, word[4])) { |
872 struct conversation *c = irc_find_chat(gc, word[3]); | 849 struct conversation *c = irc_find_chat(gc, word[3]); |
873 if (!c) | 850 if (!c) |
874 return; | 851 return FALSE; |
875 gc->buddy_chats = g_slist_remove(gc->buddy_chats, c); | 852 gc->buddy_chats = g_slist_remove(gc->buddy_chats, c); |
876 c->gc = NULL; | 853 c->gc = NULL; |
877 g_snprintf(outbuf, sizeof(outbuf), _("You have been kicked from %s: %s"), | 854 g_snprintf(outbuf, sizeof(outbuf), _("You have been kicked from %s: %s"), |
878 word[3], *word_eol[5] == ':' ? word_eol[5] + 1: word_eol[5]); | 855 word[3], *word_eol[5] == ':' ? word_eol[5] + 1: word_eol[5]); |
879 do_error_dialog(outbuf, _("IRC Error")); | 856 do_error_dialog(outbuf, _("IRC Error")); |
896 struct conversation *c; | 873 struct conversation *c; |
897 GList *r; | 874 GList *r; |
898 if (*chan == ':') | 875 if (*chan == ':') |
899 chan++; | 876 chan++; |
900 if (!(c = irc_find_chat(gc, chan))) | 877 if (!(c = irc_find_chat(gc, chan))) |
901 return; | 878 return FALSE; |
902 if (!strcmp(nick, gc->displayname)) { | 879 if (!strcmp(nick, gc->displayname)) { |
903 serv_got_chat_left(gc, c->id); | 880 serv_got_chat_left(gc, c->id); |
904 return; | 881 return FALSE; |
905 } | 882 } |
906 r = c->in_room; | 883 r = c->in_room; |
907 while (r) { | 884 while (r) { |
908 char *who = r->data; | 885 char *who = r->data; |
909 if (*who == '@') | 886 if (*who == '@') |
919 r = r->next; | 896 r = r->next; |
920 } | 897 } |
921 } else if (!strcmp(cmd, "PRIVMSG")) { | 898 } else if (!strcmp(cmd, "PRIVMSG")) { |
922 char *to, *msg; | 899 char *to, *msg; |
923 if (!*word[3]) | 900 if (!*word[3]) |
924 return; | 901 return FALSE; |
925 to = word[3]; | 902 to = word[3]; |
926 msg = *word_eol[4] == ':' ? word_eol[4] + 1 : word_eol[4]; | 903 msg = *word_eol[4] == ':' ? word_eol[4] + 1 : word_eol[4]; |
927 if (msg[0] == 1 && msg[strlen (msg) - 1] == 1) { /* ctcp */ | 904 if (msg[0] == 1 && msg[strlen (msg) - 1] == 1) { /* ctcp */ |
928 if (!g_strncasecmp(msg + 1, "DCC ", 4)) | 905 if (!g_strncasecmp(msg + 1, "DCC ", 4)) |
929 process_data_init(pdibuf, buf, word, word_eol, TRUE); | 906 process_data_init(pdibuf, buf, word, word_eol, TRUE); |
944 nick, topic); | 921 nick, topic); |
945 write_to_conv(c, buf, WFLAG_SYSTEM, NULL, time(NULL)); | 922 write_to_conv(c, buf, WFLAG_SYSTEM, NULL, time(NULL)); |
946 } | 923 } |
947 } else if (!strcmp(cmd, "WALLOPS")) { /* */ | 924 } else if (!strcmp(cmd, "WALLOPS")) { /* */ |
948 } | 925 } |
926 | |
927 return FALSE; | |
928 } | |
929 | |
930 static void irc_callback(gpointer data, gint source, GaimInputCondition condition) | |
931 { | |
932 struct gaim_connection *gc = data; | |
933 struct irc_data *idata = gc->proto_data; | |
934 int i = 0; | |
935 gchar buf[1024]; | |
936 gboolean off; | |
937 | |
938 if (!idata->online) { | |
939 /* Now lets sign ourselves on */ | |
940 account_online(gc); | |
941 serv_finish_login(gc); | |
942 | |
943 if (bud_list_cache_exists(gc)) | |
944 do_import(gc, NULL); | |
945 | |
946 /* we don't call this now because otherwise some IRC servers might not like us */ | |
947 idata->timer = g_timeout_add(20000, irc_request_buddy_update, gc); | |
948 idata->online = TRUE; | |
949 } | |
950 | |
951 i = read(idata->fd, buf, 1024); | |
952 if (i <= 0) { | |
953 hide_login_progress(gc, "Read error"); | |
954 signoff(gc); | |
955 return; | |
956 } | |
957 | |
958 idata->rxqueue = g_realloc(idata->rxqueue, i + idata->rxlen + 1); | |
959 memcpy(idata->rxqueue + idata->rxlen, buf, i); | |
960 idata->rxlen += i; | |
961 idata->rxqueue[idata->rxlen] = 0; | |
962 | |
963 while (1) { | |
964 char *d, *e; | |
965 int len; | |
966 | |
967 if (!idata->rxqueue || ((e = strchr(idata->rxqueue, '\n')) == NULL)) | |
968 return; | |
969 | |
970 len = e - idata->rxqueue + 1; | |
971 d = g_strndup(idata->rxqueue, len); | |
972 g_strchomp(d); | |
973 debug_printf("IRC S: %s\n", d); | |
974 | |
975 idata->rxlen -= len; | |
976 if (idata->rxlen) { | |
977 char *tmp = g_strdup(e + 1); | |
978 g_free(idata->rxqueue); | |
979 idata->rxqueue = tmp; | |
980 } else { | |
981 g_free(idata->rxqueue); | |
982 idata->rxqueue = NULL; | |
983 } | |
984 | |
985 off = irc_parse(gc, d); | |
986 | |
987 g_free(d); | |
988 | |
989 if (off) | |
990 return; | |
991 } | |
949 } | 992 } |
950 | 993 |
951 static void irc_login_callback(gpointer data, gint source, GaimInputCondition condition) | 994 static void irc_login_callback(gpointer data, gint source, GaimInputCondition condition) |
952 { | 995 { |
953 struct gaim_connection *gc = data; | 996 struct gaim_connection *gc = data; |
1026 struct irc_data *idata = (struct irc_data *)gc->proto_data; | 1069 struct irc_data *idata = (struct irc_data *)gc->proto_data; |
1027 gchar buf[IRC_BUF_LEN]; | 1070 gchar buf[IRC_BUF_LEN]; |
1028 | 1071 |
1029 g_snprintf(buf, sizeof(buf), "QUIT :Download Gaim [%s]\r\n", WEBSITE); | 1072 g_snprintf(buf, sizeof(buf), "QUIT :Download Gaim [%s]\r\n", WEBSITE); |
1030 irc_write(idata->fd, buf, strlen(buf)); | 1073 irc_write(idata->fd, buf, strlen(buf)); |
1074 | |
1075 if (idata->rxqueue) | |
1076 g_free(idata->rxqueue); | |
1077 idata->rxqueue = NULL; | |
1078 idata->rxlen = 0; | |
1031 | 1079 |
1032 g_free(idata->chantypes); | 1080 g_free(idata->chantypes); |
1033 g_free(idata->chanmodes); | 1081 g_free(idata->chanmodes); |
1034 g_free(idata->nickmodes); | 1082 g_free(idata->nickmodes); |
1035 | 1083 |