Annotation of OpenXM/src/kan96xx/plugin/sm1Socket.c, Revision 1.15
1.15 ! takayama 1: /* $OpenXM: OpenXM/src/kan96xx/plugin/sm1Socket.c,v 1.14 2002/10/30 13:23:06 takayama Exp $ */
1.1 maekawa 2: /* msg0s.c */
3: #include <stdio.h>
4: #include <sys/types.h>
5: #include <sys/socket.h>
6: #include <sys/time.h>
7: #include <netinet/in.h>
8: #include <netdb.h>
9:
10:
11: #include "datatype.h"
12: #include "stackm.h"
13: #include "extern.h"
14: #include "sm1Socket.h"
15:
16: extern int Quiet;
1.14 takayama 17: static int Post_debug=0;
1.1 maekawa 18: static void errorMsg1s(char *s);
1.8 takayama 19: static int getContentLength(char *s);
20: static int getReceivedContentLength(char *s);
1.6 takayama 21: #define MAX_LISTEN_QUEUE 3
1.1 maekawa 22:
23: /* [(sm1.socket) (open) [optional integer port, optional string name] ] extension ; */
24: struct object KsocketOpen(struct object obj) {
25: char serverName[1024];
26: int portNumber;
27: struct object rob = NullObject;
28: struct hostent *myhost;
29: struct sockaddr_in me;
30: int s_waiting;
31: int on;
32: int tt;
33: extern int errno;
1.14 takayama 34: extern int Post_debug;
35:
36: if ((char *)getenv("OXWEB_DEBUG") != NULL) {
37: Post_debug = 1;
38: }
1.1 maekawa 39:
40: if (obj.tag != Sarray) {
41: errorMsg1s("KsocketOpen([optional integer,optional string name])");
42: }
43: strcpy(serverName,"localhost");
44: portNumber = 0;
45: if (getoaSize(obj) >= 1) {
46: if ((getoa(obj,0)).tag != Sinteger) {
47: errorMsg1s("KsocketOpen([optional integer,optional string name]), the first argument must be an integer.");
48: }
49: portNumber = KopInteger(getoa(obj,0));
50: }
51: if (getoaSize(obj) >= 2) {
52: if ((getoa(obj,1)).tag != Sdollar) {
53: errorMsg1s("KsocketOpen([optional integer,optional string name]), the second argument must be a string.");
54: }
55: if (strlen(KopString(getoa(obj,1))) > 1023) {
56: errorMsg1s("Too long server name");
57: }
58: strcpy(serverName,KopString(getoa(obj,1)));
59: }
60:
61:
62: /* fprintf(stderr,"Hello from open.\n"); */
63: if ((myhost = gethostbyname(serverName)) == NULL) {
64: errorMsg1s("Bad server name.");
65: }
66: bzero((char *)&me,sizeof(me));
67: me.sin_family = AF_INET;
68: me.sin_port = htons(portNumber);
69: bcopy(myhost->h_addr,
1.3 takayama 70: &me.sin_addr,myhost->h_length);
1.1 maekawa 71:
72: if ((s_waiting = socket(AF_INET,SOCK_STREAM,0)) < 0) {
73: errorMsg1s("Socket allocation is failed.");
74: }
75:
76: on=1; setsockopt(s_waiting,SOL_SOCKET,SO_REUSEADDR,&on,sizeof(on));
77: /* important */
78: if (bind(s_waiting,(struct sockaddr *) &me,sizeof(me)) == -1) {
79: fprintf(stderr,"Bind error. Error no is %d. See /usr/include/sys/errno.h.\n",errno);
80: errorMsg1s("cannot bind");
81: }
82:
83: tt = sizeof(me);
84: if (getsockname(s_waiting,(struct sockaddr *)&me,&tt) < 0) {
85: fprintf(stderr,"getsockname error. Error no is %d. See /usr/include/sys/errno.h.\n",errno);
86: errorMsg1s("cannot getsockname");
87: }
88:
89:
1.6 takayama 90: if (listen(s_waiting,MAX_LISTEN_QUEUE) < 0) {
1.1 maekawa 91: errorMsg1s("Listen failed");
92: }
93: /*
1.3 takayama 94: fprintf(stderr,"Done the initialization. port =%d\n",ntohs(me.sin_port));
95: fprintf(stderr,"socket id = %d",accept(s_waiting,NULL,NULL)); */
1.1 maekawa 96: rob = newObjectArray(2);
97: putoa(rob,0,KpoInteger(s_waiting));
98: putoa(rob,1,KpoInteger(ntohs(me.sin_port)));
99: return(rob);
100:
101: }
102:
103: /* [ integer port, optional string host default localhost]
104: [ integer socketid, integer port ] */
105: struct object KsocketConnect(struct object obj) {
106: char serverName[1024];
107: int portNumber;
108: struct hostent *servhost;
109: struct sockaddr_in server;
110: int socketid;
111: struct object robj = NullObject;
112:
113: if (obj.tag != Sarray) {
114: errorMsg1s("KsocketConnect( [ integer port, optional string host default localhost])");
115: }
116: strcpy(serverName,"localhost");
117: if (getoaSize(obj) < 1) {
118: errorMsg1s("You need to specify port number.\n");
119: }
120: if (getoaSize(obj) >= 1) {
121: if ((getoa(obj,0)).tag != Sinteger) {
122: errorMsg1s("KsocketConnect([integer port,optional string host]), the first argument must be an integer.");
123: }
124: portNumber = KopInteger(getoa(obj,0));
125: }
126: if (getoaSize(obj) >= 2) {
127: if ((getoa(obj,1)).tag != Sdollar) {
128: errorMsg1s("KsocketConnect([integer port,optional string host]), the second argument must be a string.");
129: }
130: if (strlen(KopString(getoa(obj,1))) > 1023) {
131: errorMsg1s("Too long server name");
132: }
133: strcpy(serverName,KopString(getoa(obj,1)));
134: }
135:
136:
137: if ((servhost = gethostbyname(serverName)) == NULL) {
138: errorMsg1s("bad server name.\n");
139: }
140: bzero((char *)&server,sizeof(server));
141: server.sin_family = AF_INET;
142: server.sin_port = htons(portNumber);
143: bcopy(servhost->h_addr,
1.3 takayama 144: (char *)&server.sin_addr,servhost->h_length);
1.1 maekawa 145:
146: if ((socketid = socket(AF_INET,SOCK_STREAM,0)) <0) {
147: errorMsg1s("socket allocation is failed.\n");
148: }
149: if (!Quiet) {
150: fprintf(stderr,"Trying to connect port %d, ip=%x\n",ntohs(server.sin_port),server.sin_addr);
151: }
152: if (connect(socketid,(struct sockaddr *)&server,sizeof(server)) == -1) {
153: errorMsg1s("cannot connect");
154: }
155: /* fprintf(stderr,"connected.\n"); */
156: robj = newObjectArray(2);
157: putoa(robj,0,KpoInteger(socketid));
158: putoa(robj,1,KpoInteger(portNumber));
159: return(robj);
160: }
161:
162: /* [ integer socketid ]
163: [ integer newsocketid ] */
164: struct object KsocketAccept(struct object obj) {
165: struct object obj1;
166: struct object obj2;
167: struct object robj;
168: int s, news;
169:
170: if (obj.tag != Sarray) {
171: errorMsg1s("KsocketAccept([integer socketid])");
172: }
173: if (getoaSize(obj) < 1) {
174: errorMsg1s("KsocketAccept([integer socketid])");
175: }
176: obj1 = getoa(obj,0);
177: if (obj1.tag != Sinteger ) {
178: errorMsg1s("KsocketAccept([integer socketid]), argument must be integer.");
179: }
180: s = KopInteger(obj1);
181: if ((news = accept(s,NULL,NULL)) < 0) {
1.15 ! takayama 182: fprintf(stderr,"Error in accept. Retrying (KsocketAccept).\n");
! 183: /* Code added for strange behavior on cygwin. */
! 184: if ((news = accept(s,NULL,NULL)) < 0) {
! 185: errorMsg1s("Error in accept. Retry failed.");
! 186: }
1.1 maekawa 187: }
188: if (close(s) < 0) {
189: errorMsg1s("Error in closing the old socket.");
190: }
191: robj = newObjectArray(1);
192: putoa(robj,0,KpoInteger(news));
193: return(robj);
194: }
195:
1.13 takayama 196: /* [ integer socketid ]
197: [ integer newsocketid ] */
198: /* It does not close the listening socket. You can call it as
199: ls = open.
200: fd=accept2(ls). close(fd).
201: fd=accept2(ls). close(fd).
202: ....
203: */
204: struct object KsocketAccept2(struct object obj) {
205: struct object obj1;
206: struct object obj2;
207: struct object robj;
208: int s, news;
209:
210: if (obj.tag != Sarray) {
211: errorMsg1s("KsocketAccept([integer socketid])");
212: }
213: if (getoaSize(obj) < 1) {
214: errorMsg1s("KsocketAccept([integer socketid])");
215: }
216: obj1 = getoa(obj,0);
217: if (obj1.tag != Sinteger ) {
218: errorMsg1s("KsocketAccept([integer socketid]), argument must be integer.");
219: }
220: s = KopInteger(obj1);
221: if ((news = accept(s,NULL,NULL)) < 0) {
1.15 ! takayama 222: fprintf(stderr,"Error in accept. Retrying (KsocketAccept2).\n");
! 223: /* Code added for strange behavior on cygwin. */
! 224: if ((news = accept(s,NULL,NULL)) < 0) {
! 225: errorMsg1s("Error in accept. Retry failed.");
! 226: }
1.13 takayama 227: }
228: if (close(s) < 0) {
229: errorMsg1s("Error in closing the old socket.");
230: }
231: robj = newObjectArray(1);
232: putoa(robj,0,KpoInteger(news));
233: return(robj);
234: }
235:
1.1 maekawa 236: int KsocketSelect0(int fd,int t) {
237: fd_set readfds;
238: struct timeval timeout;
239: extern int errno;
240: FD_ZERO(&readfds);
241: FD_SET(fd,&readfds);
242: timeout.tv_sec = 0;
243: timeout.tv_usec = (long) t;
244: if (t >= 0) {
245: if (select(fd+1,&readfds,(fd_set *)NULL,(fd_set *)NULL,&timeout)<0) {
246: /* It must be fd+1 !, Not fd. */
247: fprintf(stderr,"Select error. Error no is %d. See /usr/include/sys/errno.h.\n",errno);
248: errorMsg1s("KsocketSelect0() : select failed.");
249: return(0);
250: }
251: }else{ /* block */
252: if (select(fd+1,&readfds,(fd_set *)NULL,(fd_set *)NULL,(struct timeval *)NULL)<0) {
253: errorMsg1s("KsocketSelect0() : select failed.");
254: fprintf(stderr,"Select error. Error no is %d. See /usr/include/sys/errno.h.\n",errno);
255: return(0);
256: }
257: }
258: if (FD_ISSET(fd,&readfds)) return(1);
259: else return(0);
260: }
261:
262: /* [ integer socketid optional integer timeout default 0]
263: integer true or false
264: */
265: struct object KsocketSelect(struct object obj) {
266: struct object robj;
267: struct object ob1;
268: struct object ob2;
269: if (obj.tag != Sarray) {
270: errorMsg1s("KsocketSelect([ integer socketid optional integer timeout default 0]");
271: }
272: if (getoaSize(obj) < 1) {
273: errorMsg1s("KsocketSelect([ integer socketid optional integer timeout default 0]");
274: }
275: if (getoaSize(obj) >= 1) {
276: ob1 = getoa(obj,0);
277: ob2 = KpoInteger(0); /* default value */
278: }
279: if (getoaSize(obj) >= 2) {
280: ob2 = getoa(obj,1);
281: }
282: if (ob1.tag != Sinteger) {
283: errorMsg1s("KsocketSelect([ integer socketid optional integer timeout default 0] : the first argument must be an integer.");
284: }
285: if (ob2.tag != Sinteger) {
286: errorMsg1s("KsocketSelect([ integer socketid optional integer timeout default 0] : the second argument must be an integer.");
287: }
288: robj = KpoInteger( KsocketSelect0(KopInteger(ob1),KopInteger(ob2)) );
289: return(robj);
290: }
291:
292: struct object KsocketSelectMulti(struct object obj)
1.3 takayama 293: /* [ [integer socketid1, integer socketid2, ...]
1.1 maekawa 294: optional integer timeout default 0]
295: [ result1, result2, ....]
296: */
297: {
298: struct object robj;
299: struct object ob1;
300: struct object ob2;
301: struct object ob3;
302: int size,i,fd,p,t;
303: fd_set readfds;
304: struct timeval timeout;
305: extern errno;
306: if (obj.tag != Sarray) {
307: errorMsg1s("KsocketSelectMulti([[sid1, sid2,...] optional integer timeout default 0]");
308: }
309: if (getoaSize(obj) < 1) {
310: errorMsg1s("KsocketSelectMulti([[sid1, sid2,...] optional integer timeout default 0]");
311: }
312: if (getoaSize(obj) >= 1) {
313: ob1 = getoa(obj,0);
314: ob2 = KpoInteger(0); /* default value */
315: }
316: if (getoaSize(obj) >= 2) {
317: ob2 = getoa(obj,1);
318: }
319: if (ob1.tag != Sarray) {
320: errorMsg1s("KsocketSelectMulti([[sid1, sid2, ...] optional integer timeout default 0] : the first argument must be an array.");
321: }
322: if (ob2.tag != Sinteger) {
323: errorMsg1s("KsocketSelectMulti([[sid1, sid2, ...] optional integer timeout default 0] : the second argument must be an integer.");
324: }
325: FD_ZERO(&readfds);
326: timeout.tv_sec = 0; t = KopInteger(ob2);
327: timeout.tv_usec = (long)t;
328:
329: size = getoaSize(ob1);
330: if (size < 1) {
331: errorMsg1s("KsocketSelectMulti: the first argument must be a non-empty array of integers.");
332: }
333: fd = 0;
334:
335: for (i=0; i<size; i++) {
336: ob3 = getoa(ob1,i);
337: if (ob3.tag != Sinteger) {
338: errorMsg1s("KsocketSelectMulti: the first argument must be an array of integers.");
339: }
340: p = KopInteger(ob3);
341: if (p > fd) fd = p;
342: FD_SET(p,&readfds);
343: /* printf("p = %d, fd=%d",p,fd); */
344: }
345:
346: if (t >= 0) {
347: if (select(fd+1,&readfds,(fd_set *)NULL,(fd_set *)NULL,&timeout)<0) {
348: /* It must be fd+1 !, Not fd. */
349: fprintf(stderr,"Select error. Error no is %d. See /usr/include/sys/errno.h.\n",errno);
350: errorMsg1s("KsocketSelectMulti() : select failed.");
351: }
352: }else{ /* block */
353: if (select(fd+1,&readfds,(fd_set *)NULL,(fd_set *)NULL,(struct timeval *)NULL)<0) {
354: fprintf(stderr,"Select error. Error no is %d. See /usr/include/sys/errno.h.\n",errno);
355: errorMsg1s("KsocketSelectMulti() : (block) select failed.");
356: }
357: }
358: robj = newObjectArray(size);
359: for (i=0; i<size; i++) {
360: if (FD_ISSET(KopInteger(getoa(ob1,i)),&readfds)) {
361: putoa(robj,i,KpoInteger(1));
362: }else{
363: putoa(robj,i,KpoInteger(0));
364: }
365: }
366:
367: return(robj);
368: }
369:
370:
371:
372:
373: static char Data00[1024];
374: /* [ integer socketid ]
375: string data
376: */
377: struct object KsocketRead(struct object obj) {
378: struct object ob1;
379: struct object robj = NullObject;
380: static int datasize = 1024;
381: static char *data = Data00;
382: char *tmp;
383: char *r;
384: int n;
385: int socketid;
386: int totalsize;
387:
388: if (obj.tag != Sarray) {
389: errorMsg1s("KsocketRead([integer socketid])");
390: }
391: if (getoaSize(obj) < 1) {
392: errorMsg1s("KsocketRead([integer socketid])");
393: }
394: ob1 = getoa(obj,0);
395: if (ob1.tag != Sinteger) {
396: errorMsg1s("KsocketRead([integer socketid]) : the argument must be integer.");
397: }
398: socketid = KopInteger(ob1);
399:
400: totalsize = 0;
401:
402: while (KsocketSelect0(socketid,0)) {
403: if (datasize - totalsize > 0) {
404: n = read(socketid,data+totalsize,datasize-totalsize);
405: if (n < 0) {
1.3 takayama 406: errorMsg1s("Read error.");
1.1 maekawa 407: }
408: if (n < datasize-totalsize) {
1.3 takayama 409: totalsize += n;
410: break;
1.1 maekawa 411: }else{ totalsize += n; }
412: if (totalsize == 0) {
1.3 takayama 413: errorMsg1s("Select returns 1, but there is no data to read.");
1.1 maekawa 414: }
415: }else { /* increase the datasize */
416: tmp = (char *)GC_malloc(sizeof(char)*2*datasize);
417: /*I should use GC_malloc_atomic and free after finishing this function?*/
418: if (tmp == (char *)NULL) errorMsg1s("Out of Memory.");
419: bcopy(data,tmp,totalsize);
420: data = tmp;
421: datasize = 2*datasize;
422: }
423: }
424:
1.5 takayama 425: r = (char *)GC_malloc(sizeof(char)*(totalsize+1));
1.1 maekawa 426: if (r == (char *)NULL) errorMsg1s("Out of Memory.");
427: bcopy(data,r,totalsize);
1.5 takayama 428: r[totalsize] = 0;
429: robj = KpoString(r); /* BUG: it works only for reading string from TCP/IP
430: stream. */
1.1 maekawa 431:
432: return(robj);
433:
434: }
435:
436: /* [ integer socketid, string data ]
437: integer */
438: struct object KsocketWrite(struct object obj) {
439: struct object ob1;
440: struct object ob2;
441: int socketid;
442: int r;
443: if (obj.tag != Sarray) {
444: errorMsg1s("KsocketWrite([integer socketid, string data])");
445: }
446: if (getoaSize(obj) < 2) {
447: errorMsg1s("KsocketWrite([integer socketid, string data])");
448: }
449: ob1 = getoa(obj,0);
450: ob2 = getoa(obj,1);
451: if (ob1.tag != Sinteger) {
452: errorMsg1s("KsocketWrite([integer socketid, string data]) : the first argument must be an integer.");
453: }
454: socketid = KopInteger(ob1);
455: if (ob2.tag != Sdollar) {
456: errorMsg1s("KsocketWrite([integer socketid, string data]) : the second argument must be a string.");
457: }
458: r = write(socketid,KopString(ob2), strlen(KopString(ob2)));
459: return(KpoInteger(r));
460:
461: }
462: struct object KsocketClose(struct object obj) {
463: int socketid;
464: struct object ob1;
465: if (obj.tag != Sarray) {
466: errorMsg1s("KsocketClose([ integer socketid ])");
467: }
468: if (getoaSize(obj) != 1) {
469: errorMsg1s("KsocketClose([ integer socketid ])");
470: }
471: ob1 = getoa(obj,0);
472: if (ob1.tag != Sinteger) {
473: errorMsg1s("KsocketClose([ INTEGER socketid ])");
474: }
475: socketid = KopInteger(ob1);
476: return(KpoInteger(close(socketid)));
477: }
478:
479:
480: static void errorMsg1s(char *s) {
481: fprintf(stderr,"%s\n",s);
482: errorKan1("msg1s.c: %s\n",s);
483: }
484:
485:
486: /**************** new 1997, 11/23 *******************/
487: struct object KsocketReadByte(struct object obj);
488: struct object KsocketWriteByte(struct object obj);
489:
490: struct object KsocketReadByte(struct object obj) {
491: struct object ob1;
492: struct object robj = NullObject;
493: char data[2];
494: char *tmp;
495: char *r;
496: int n;
497: int socketid;
498:
499:
500: if (obj.tag != Sarray) {
501: errorMsg1s("KsocketReadByte([integer socketid])");
502: }
503: if (getoaSize(obj) < 1) {
504: errorMsg1s("KsocketReadByte([integer socketid])");
505: }
506: ob1 = getoa(obj,0);
507: if (ob1.tag != Sinteger) {
508: errorMsg1s("KsocketReadByte([integer socketid]) : the argument must be integer.");
509: }
510: socketid = KopInteger(ob1);
511:
512:
513: n = read(socketid,data,1);
514: if (n < 0) {
515: errorMsg1s("Read error.");
516: robj = KpoInteger(-1);
517: return(robj);
518: }
519: if (n == 0) {
520: errorMsg1s("Read returned without data.");
521: }
522:
523: robj = KpoInteger((int)((unsigned char)data[0]));
524: return(robj);
525:
526: }
527:
528: /* [ integer socketid, int ]
529: integer */
530: struct object KsocketWriteByte(struct object obj) {
531: struct object ob1;
532: struct object ob2;
533: int socketid;
1.4 takayama 534: int r,i,n,kk,r0;
535: #define DATA_SIZE 1024
536: char data[DATA_SIZE];
1.1 maekawa 537: if (obj.tag != Sarray) {
1.4 takayama 538: errorMsg1s("KsocketWriteByte([integer socketid, int | array of int])");
1.1 maekawa 539: }
540: if (getoaSize(obj) < 2) {
1.4 takayama 541: errorMsg1s("KsocketWriteByte([integer socketid, int | array of int])");
1.1 maekawa 542: }
543: ob1 = getoa(obj,0);
544: ob2 = getoa(obj,1);
545: if (ob1.tag != Sinteger) {
1.4 takayama 546: errorMsg1s("KsocketWriteByte([integer socketid, int | array of int]) : the first argument must be an integer.");
1.1 maekawa 547: }
548: socketid = KopInteger(ob1);
1.4 takayama 549: if (ob2.tag != Sinteger && ob2.tag != Sarray) {
550: errorMsg1s("KsocketWriteByte([integer socketid, int | array of int]) : the second argument must be an integer or an array of integers.");
551: }
552: if (ob2.tag == Sinteger) {
553: data[0] = KopInteger(ob2);
554: r = write(socketid,data, 1);
555: }else{
556: n = getoaSize(ob2); kk = 0; r = 0;
557: for (i=0; i<n; i++) {
558: if (getoa(ob2,i).tag != Sinteger)
559: errorMsg1s("KsocketWriteByte([integer socketid, int | array of int]) : elements of the second argument must be integers.");
560: data[kk] = KopInteger(getoa(ob2,i));
561: kk++;
562: if (kk >= DATA_SIZE) {
563: r0 = write(socketid,data,kk);
564: if (r0 != kk) {
565: fprintf(stderr,"Warning: Could not write to the socket.\n");
566: return(KpoInteger(r+r0));
567: }
568: r += r0;
569: kk = 0;
570: }
571: }
572: if (kk > 0) {
573: r0 = write(socketid,data,kk);
574: if (r0 != kk) {
575: fprintf(stderr,"Warning: Could not write to the socket.\n");
576: return(KpoInteger(r+r0));
577: }
578: r += r0;
579: }
1.1 maekawa 580: }
581: return(KpoInteger(r));
582: }
583:
1.7 takayama 584: struct object KsocketReadHTTP(struct object socketObj) {
585: /* Read until two empty line appears. */
1.5 takayama 586: struct object ob;
1.13 takayama 587: struct object ob1;
588: struct object nob;
1.5 takayama 589: char *s;
590: char *sss;
591: char *tmp;
592: int i;
593: int flag;
1.7 takayama 594: int flagmax = 1;
1.5 takayama 595: int datasize;
1.7 takayama 596: int last;
1.8 takayama 597: int contentLength=-1;
1.13 takayama 598: int socketid;
1.14 takayama 599: extern int Post_debug;
1.13 takayama 600: nob = NullObject;
601:
602: if (socketObj.tag != Sarray) {
603: errorMsg1s("KsocketReadHTTP([integer socketid])");
604: }
605: if (getoaSize(socketObj) < 1) {
606: errorMsg1s("KsocketReadHTTP([integer socketid])");
607: }
608: ob1 = getoa(socketObj,0);
609: if (ob1.tag != Sinteger) {
610: errorMsg1s("KsocketReadHTTP([integer socketid]) : the argument must be integer.");
611: }
612: socketid = KopInteger(ob1);
613:
614: if (KsocketSelect0(socketid,-1) != 1) {
615: return(nob);
616: }
1.5 takayama 617: ob = KsocketRead(socketObj);
618: s = KopString(ob);
1.8 takayama 619: if (strncmp(s,"POST",4) == 0) flagmax=2; /* for IE */
1.7 takayama 620: else flagmax=1;
1.5 takayama 621: flag = 0;
622: for (i=strlen(s)-1; i>=0; i--) {
623: if ((s[i] == '\n') && (i==0)) {
1.7 takayama 624: ++flag;
1.5 takayama 625: }else if ((s[i] == '\n') && (s[i-1] == '\n')) {
1.7 takayama 626: ++flag;
1.5 takayama 627: }else if ((s[i] == 0xd) && (s[i+1] == 0xa) && (i == 0)) {
1.7 takayama 628: ++flag;
1.5 takayama 629: }else if ((s[i] == 0xa) && (s[i-1] == 0xd) && (s[i+1] == 0xd) && (s[i+2] == 0xa)) {
1.7 takayama 630: ++flag;
1.5 takayama 631: }
632: }
1.7 takayama 633: if (flag >= flagmax) return ob;
1.5 takayama 634: datasize = strlen(s);
635: sss = s;
1.7 takayama 636: if ((s[strlen(s)-1] == '\n') ||
637: (s[strlen(s)-2] == 0xd) && (s[strlen(s)-1] == 0xa)) {
638: last = 1;
639: }else last = 0;
1.5 takayama 640:
1.7 takayama 641: while (flag < flagmax) {
1.8 takayama 642: contentLength = getContentLength(sss);
643: if (contentLength != -1) {
644: if (contentLength <= getReceivedContentLength(sss)) {
645: break;
646: }
647: }
1.14 takayama 648: if (Post_debug) {
649: fprintf(stderr,"Waiting in socketReadBlock. flagmax(0d,0a)=%d, content-length=%d, received content-length=%d\n",flagmax,contentLength,getReceivedContentLength(sss));
650: }
1.13 takayama 651: if (strlen(s) == 0) {
652: fprintf(stderr,"No data. Perhaps connection is closed by foreign host.\n");
653: return nob;
1.5 takayama 654: }else{
655: /* for debugging. */
1.14 takayama 656: if (Post_debug) {
657: for (i=0; i<strlen(sss); i++) {
658: if ((sss[i] >= ' ') && (sss[i] < 0x7f)) {
659: fprintf(stderr,"%c",sss[i]);
660: }else{
661: fprintf(stderr,"(%3x)",sss[i]);
662: if (sss[i] == 0xa) fprintf(stderr,"\n");
663: }
664:
1.8 takayama 665: }
1.14 takayama 666: fprintf(stderr,"\n");
1.5 takayama 667: }
668: }
1.13 takayama 669:
670: if (KsocketSelect0(socketid,-1) != 1) {
671: return nob;
672: }
1.5 takayama 673: ob = KsocketRead(socketObj);
674: s = KopString(ob);
675: for (i=strlen(s)-1; i>=0; i--) {
1.7 takayama 676: if ((s[i] == '\n') && (i==0) && last) {
677: ++flag;
1.5 takayama 678: }else if ((s[i] == '\n') && (s[i-1] == '\n')) {
1.7 takayama 679: ++flag;
680: }else if ((s[i] == 0xd) && (s[i+1] == 0xa) && (i==0) && last) {
681: ++flag;
1.5 takayama 682: }else if ((s[i] == 0xa) && (s[i-1] == 0xd) && (s[i+1] == 0xd) && (s[i+2] == 0xa)) {
1.7 takayama 683: ++flag;
1.5 takayama 684: }
685: }
686: if (datasize-1 <= strlen(sss)+strlen(s)) {
687: tmp = (char *)GC_malloc(sizeof(char)*2*(datasize+strlen(s))+1);
688: if (tmp == (char *)NULL) errorMsg1s("Out of Memory.");
689: strcpy(tmp,sss);
690: strcat(tmp,s);
691: datasize = 2*(datasize+strlen(s));
692: sss = tmp;
693: }else{
694: strcat(sss,s);
695: }
1.7 takayama 696:
697: if ((s[strlen(s)-1] == '\n') ||
698: (s[strlen(s)-2] == 0xd) && (s[strlen(s)-1] == 0xa)) {
699: last = 1;
700: }else last = 0;
701:
1.5 takayama 702: }
703:
704: return KpoString(sss);
705:
706: }
707:
1.1 maekawa 708: struct object Kplugin_sm1Socket(char *key,struct object obj) {
709: struct object robj = NullObject;
710: if (strcmp(key,"open") == 0) {
711: robj = KsocketOpen(obj);
712: }else if (strcmp(key,"connect") == 0) {
713: robj = KsocketConnect(obj);
714: }else if (strcmp(key,"accept") == 0) {
715: robj = KsocketAccept(obj);
1.13 takayama 716: }else if (strcmp(key,"accept2") == 0) {
717: robj = KsocketAccept2(obj);
1.1 maekawa 718: }else if (strcmp(key,"select") == 0) {
719: robj = KsocketSelect(obj);
720: }else if (strcmp(key,"mselect") == 0) {
721: robj = KsocketSelectMulti(obj);
722: }else if (strcmp(key,"read") == 0) {
723: robj = KsocketRead(obj);
1.7 takayama 724: }else if (strcmp(key,"readHTTP") == 0) {
725: robj = KsocketReadHTTP(obj);
1.11 takayama 726: }else if (strcmp(key,"gethostname") == 0) {
727: robj = KsocketGetHostName();
728: }else if (strcmp(key,"write") == 0) {
1.1 maekawa 729: robj = KsocketWrite(obj);
730: }else if (strcmp(key,"read") == 0) {
731: robj = KsocketRead(obj);
732: }else if (strcmp(key,"readByte") == 0) {
733: robj = KsocketReadByte(obj);
734: }else if (strcmp(key,"writeByte") == 0) {
735: robj = KsocketWriteByte(obj);
736: }else if (strcmp(key,"close") == 0) {
737: robj = KsocketClose(obj);
738: }else {
739: errorMsg1s("Unknown tag for sm1.socket");
740: }
741: return(robj);
742: }
743:
744:
1.8 takayama 745: static int getContentLength(char *s) {
746: int n;
1.10 takayama 747: int i,j;
1.8 takayama 748: int len = -1;
1.10 takayama 749: char *s1 = "content-length:";
750: char s0[256];
751: int m;
752: m = strlen(s1);
1.8 takayama 753: n = strlen(s);
754: for (i=0; i<n; i++) {
1.10 takayama 755: strncpy(s0,&(s[i]),m+1);
756: for (j=0; j<m; j++) {
757: if ((s0[j] >= 'A') && (s0[j] <= 'Z')) s0[j] = s0[j]+0x20;
758: }
759: if (strncmp(s0,s1,strlen(s1)) == 0) {
760: sscanf(&(s[i+strlen(s1)]),"%d",&len);
761: break;
762: }
1.8 takayama 763: }
764: return len;
765: }
766: static int getReceivedContentLength(char *s) {
767: int n;
768: int i;
769: int start;
770: start = -1;
771: n = strlen(s);
772: for (i=0; i<n; i++) {
773: if ((s[i] == '\n') && (s[i+1] == '\n')) {
774: start = i+2; break;
775: }else if ((s[i] == 0xd) && (s[i+1] == 0xa) && (s[i+2] == 0xd) && (s[i+3] == 0xa)) {
776: start = i+4;
777: }
778: }
779: if (start == -1) return 0;
780: return (n-start);
781: }
1.1 maekawa 782:
783:
1.11 takayama 784: struct object KsocketGetHostName(void) {
785: char name[1024];
786: char *s;
787: struct object rob = NullObject;
788: if (gethostname(name,1023) != 0) {
789: return rob;
790: }
791: s = (char *)GC_malloc(sizeof(char)*(strlen(name)+2));
792: if (s == (char *)NULL) errorMsg1s("Out of Memory.");
793: strcpy(s,name);
794: return(KpoString(s));
795: }
1.1 maekawa 796:
797:
798:
799:
800:
801:
FreeBSD-CVSweb <freebsd-cvsweb@FreeBSD.org>