Annotation of libwww/Library/src/HTWriter.c, revision 2.9
2.1 timbl 1: /* FILE WRITER HTWrite.c
2: ** ===========
3: **
4: */
5: #include "HTWriter.h"
6:
7: #define BUFFER_SIZE 4096 /* Tradeoff */
8:
9: #include "HTUtils.h"
10: #include "tcp.h"
11:
12: /* HTML Object
13: ** -----------
14: */
15:
16: struct _HTStream {
17: CONST HTStreamClass * isa;
18:
19: int soc;
20: char *write_pointer;
21: char buffer[BUFFER_SIZE];
2.8 luotonen 22: BOOL leave_open;
2.1 timbl 23: #ifdef NOT_ASCII
24: BOOL make_ascii; /* Are we writing to the net? */
25: #endif
26: };
27:
28:
29: /* Write the buffer out to the socket
30: ** ----------------------------------
31: */
32:
2.2 timbl 33: PRIVATE void flush ARGS1(HTStream *, me)
2.1 timbl 34: {
2.2 timbl 35: char *read_pointer = me->buffer;
36: char *write_pointer = me->write_pointer;
2.1 timbl 37:
2.9 ! frystyk 38: #ifdef NOT_ASCII
2.2 timbl 39: if (me->make_ascii) {
2.1 timbl 40: char * p;
2.2 timbl 41: for(p = me->buffer; p < me->write_pointer; p++)
2.1 timbl 42: *p = TOASCII(*p);
43: }
44: #endif
45: while (read_pointer < write_pointer) {
46: int status;
2.9 ! frystyk 47: #ifdef OLD_CODE
2.7 timbl 48: status = NETWRITE(me->soc, me->buffer, /* Put timeout? @@@ */
2.1 timbl 49: write_pointer - read_pointer);
2.9 ! frystyk 50: #endif /* OLD_CODE */
! 51: status = NETWRITE(me->soc, read_pointer, write_pointer - read_pointer);
2.1 timbl 52: if (status<0) {
53: if(TRACE) fprintf(stderr,
2.5 timbl 54: "HTWrite: Error: write() on socket returns %d !!!\n", status);
2.1 timbl 55: return;
56: }
2.9 ! frystyk 57: read_pointer += status;
2.1 timbl 58: }
2.2 timbl 59: me->write_pointer = me->buffer;
2.1 timbl 60: }
61:
62:
63: /*_________________________________________________________________________
64: **
65: ** A C T I O N R O U T I N E S
66: */
67:
68: /* Character handling
69: ** ------------------
70: */
71:
2.2 timbl 72: PRIVATE void HTWriter_put_character ARGS2(HTStream *, me, char, c)
2.1 timbl 73: {
2.2 timbl 74: if (me->write_pointer == &me->buffer[BUFFER_SIZE]) flush(me);
75: *me->write_pointer++ = c;
2.1 timbl 76: }
77:
78:
79:
80: /* String handling
81: ** ---------------
82: **
83: ** Strings must be smaller than this buffer size.
84: */
2.2 timbl 85: PRIVATE void HTWriter_put_string ARGS2(HTStream *, me, CONST char*, s)
2.1 timbl 86: {
87: int l = strlen(s);
2.2 timbl 88: if (me->write_pointer + l > &me->buffer[BUFFER_SIZE]) flush(me);
89: strcpy(me->write_pointer, s);
90: me->write_pointer = me->write_pointer + l;
2.1 timbl 91: }
92:
93:
94: /* Buffer write. Buffers can (and should!) be big.
95: ** ------------
96: */
2.2 timbl 97: PRIVATE void HTWriter_write ARGS3(HTStream *, me, CONST char*, s, int, l)
2.1 timbl 98: {
99:
100: CONST char *read_pointer = s;
101: CONST char *write_pointer = s+l;
102:
2.2 timbl 103: flush(me); /* First get rid of our buffer */
2.1 timbl 104:
2.9 ! frystyk 105: #ifdef NOT_ASCII
! 106: if (me->make_ascii) {
! 107: char * p;
! 108: for(p = me->buffer; p < me->write_pointer; p++)
! 109: *p = TOASCII(*p);
! 110: }
! 111: #endif
2.1 timbl 112: while (read_pointer < write_pointer) {
2.2 timbl 113: int status = NETWRITE(me->soc, read_pointer,
2.1 timbl 114: write_pointer - read_pointer);
115: if (status<0) {
116: if(TRACE) fprintf(stderr,
117: "HTWriter_write: Error on socket output stream!!!\n");
118: return;
119: }
120: read_pointer = read_pointer + status;
121: }
122: }
123:
124:
125:
126:
127: /* Free an HTML object
128: ** -------------------
129: **
130: ** Note that the SGML parsing context is freed, but the created object is not,
131: ** as it takes on an existence of its own unless explicitly freed.
132: */
2.2 timbl 133: PRIVATE void HTWriter_free ARGS1(HTStream *, me)
2.1 timbl 134: {
2.5 timbl 135: flush(me);
2.8 luotonen 136: if (!me->leave_open)
137: NETCLOSE(me->soc);
2.2 timbl 138: free(me);
2.1 timbl 139: }
140:
2.6 timbl 141: PRIVATE void HTWriter_abort ARGS2(HTStream *, me, HTError, e)
2.1 timbl 142: {
2.5 timbl 143: HTWriter_free(me);
2.1 timbl 144: }
145:
146:
147: /* Structured Object Class
148: ** -----------------------
149: */
2.4 timbl 150: PRIVATE CONST HTStreamClass HTWriter = /* As opposed to print etc */
2.1 timbl 151: {
152: "SocketWriter",
153: HTWriter_free,
2.5 timbl 154: HTWriter_abort,
2.6 timbl 155: HTWriter_put_character, HTWriter_put_string,
2.1 timbl 156: HTWriter_write
157: };
158:
159:
160: /* Subclass-specific Methods
161: ** -------------------------
162: */
163:
164: PUBLIC HTStream* HTWriter_new ARGS1(int, soc)
165: {
2.8 luotonen 166: HTStream* me = (HTStream*)calloc(1,sizeof(*me));
2.2 timbl 167: if (me == NULL) outofmem(__FILE__, "HTML_new");
168: me->isa = &HTWriter;
2.1 timbl 169:
170: #ifdef NOT_ASCII
2.2 timbl 171: me->make_ascii = NO;
2.1 timbl 172: #endif
2.2 timbl 173: me->soc = soc;
174: me->write_pointer = me->buffer;
175: return me;
2.1 timbl 176: }
177:
2.8 luotonen 178: PUBLIC HTStream* HTWriter_newNoClose ARGS1(int, soc)
179: {
180: HTStream * me = HTWriter_new(soc);
181: if (me) me->leave_open = YES;
182: return me;
183: }
184:
185:
2.1 timbl 186: /* Subclass-specific Methods
187: ** -------------------------
188: */
189:
190: PUBLIC HTStream* HTASCIIWriter ARGS1(int, soc)
191: {
2.8 luotonen 192: HTStream* me = (HTStream*)calloc(1,sizeof(*me));
2.2 timbl 193: if (me == NULL) outofmem(__FILE__, "HTML_new");
194: me->isa = &HTWriter;
2.1 timbl 195:
196: #ifdef NOT_ASCII
2.2 timbl 197: me->make_ascii = YES;
2.1 timbl 198: #endif
2.2 timbl 199: me->soc = soc;
200: me->write_pointer = me->buffer;
201: return me;
2.1 timbl 202: }
2.2 timbl 203:
Webmaster