From 35942878c24b8054c81ff8d0dbb95cfb62e2c5b1 Mon Sep 17 00:00:00 2001 From: leitner Date: Thu, 13 Mar 2014 22:25:20 +0000 Subject: [PATCH] $ make WERROR=-Werror now builds with -Werror add some single char escaping routines to fmt.h pull in html5 entities from w3c and use those to do a proper scan_html decoding fix an off-by-one in fmt_to_array add a ton of unit tests for the fmt routines --- .cvsignore | 1 + GNUmakefile | 16 +- Makefile | 5 + ent.c | 228 +++ entities.json | 2233 +++++++++++++++++++++++ fmt.h | 31 +- fmt/fmt_escapecharc.c | 36 + fmt/fmt_escapecharhtml.c | 9 + fmt/fmt_escapecharjson.c | 47 + fmt/fmt_escapecharquotedprintable.c | 11 + fmt/fmt_escapecharquotedprintableutf8.c | 10 + fmt/fmt_escapecharxml.c | 33 + test/marshal.c | 24 + test/textcode.c | 7 + textcode/fmt_to_array.c | 2 +- textcode/scan_html.c | 58 +- tryalloca.c | 4 +- trybsdsf.c | 2 + tryepoll.c | 4 +- tryip6.c | 4 +- tryn2i.c | 2 + tryscope.c | 4 +- trysendfile.c | 2 + trysigio.c | 2 + trysl.c | 4 +- trysocket.c | 4 +- 26 files changed, 2759 insertions(+), 24 deletions(-) create mode 100644 ent.c create mode 100644 entities.json create mode 100644 fmt/fmt_escapecharc.c create mode 100644 fmt/fmt_escapecharhtml.c create mode 100644 fmt/fmt_escapecharjson.c create mode 100644 fmt/fmt_escapecharquotedprintable.c create mode 100644 fmt/fmt_escapecharquotedprintableutf8.c create mode 100644 fmt/fmt_escapecharxml.c diff --git a/.cvsignore b/.cvsignore index 875e7bd..35eb6f0 100644 --- a/.cvsignore +++ b/.cvsignore @@ -22,3 +22,4 @@ trysendfile havealloca.h uudecode haveuint128.h +ent diff --git a/GNUmakefile b/GNUmakefile index 065ae5a..973c049 100644 --- a/GNUmakefile +++ b/GNUmakefile @@ -13,7 +13,7 @@ LIBS=byte.a fmt.a scan.a str.a uint.a open.a stralloc.a unix.a socket.a \ buffer.a mmap.a taia.a tai.a dns.a case.a mult.a array.a io.a \ textcode.a cdb.a -all: $(LIBS) libowfat.a libsocket t +all: ent $(LIBS) libowfat.a libsocket t CROSS= #CROSS=i686-mingw- @@ -21,9 +21,13 @@ CC=$(CROSS)gcc CFLAGS=-pipe -W -Wall -O2 -fomit-frame-pointer #CFLAGS=-pipe -Os -march=pentiumpro -mcpu=pentiumpro -fomit-frame-pointer -fschedule-insns2 -Wall +ent: ent.c + gcc -g -o ent ent.c + # CFLAGS += -fstrict-aliasing -Wstrict-aliasing=2 -CFLAGS += -D_REENTRANT +WERROR= +CFLAGS += -D_REENTRANT $(WERROR) # startrip ifneq ($(DEBUG),) @@ -326,3 +330,11 @@ windoze: windoze64: $(MAKE) DIET= CROSS=x86_64-mingw32- + +update: + dl -n http://www.w3.org/TR/html5/entities.json + +entities.h: entities.json ent + ./ent + +scan_html.o: entities.h diff --git a/Makefile b/Makefile index 6fb68e2..c3d3add 100644 --- a/Makefile +++ b/Makefile @@ -836,3 +836,8 @@ windoze: windoze64: $(MAKE) DIET= CROSS=x86_64-mingw32- + +entities.h: entities.json ent + ./ent + +scan_html.o: entities.h diff --git a/ent.c b/ent.c new file mode 100644 index 0000000..4cb02a7 --- /dev/null +++ b/ent.c @@ -0,0 +1,228 @@ +#include +#include +#include +#include +#include "scan.h" +#include + +#include "scan/scan_ulong.c" +#include "scan/scan_ulongn.c" +#include "fmt/fmt_utf8.c" +#include "fmt/fmt_escapecharc.c" + +char tmp[20]; +char tmp2[20]; +size_t n,m; +unsigned long l; + +struct entity { + const char* entity; + char utf8[10]; + struct entity* next; +}* root,** cur=&root; + +struct letter { + char c; + struct letters* weiter; + uint32_t marshaled; // lower 8 bits: char. rest: ofs from start of marshaled blob +}; + +struct letters { + size_t n; + struct letter liste[256]; +}; + +struct letters* d; +size_t nodes,datasize; + +void addword(struct letters** s,const char* t, void* pointer) { + size_t i; + if (!*s) { + *s=malloc(sizeof(**s)); + memset(*s,0,sizeof(**s)); + (*s)->liste[0].c='?'; + } + i=(unsigned char)*t; + if ((*s)->liste[i].c==*t) { + if (!*t) { + datasize+=strlen((char*)pointer)+1; + (*s)->liste[i].weiter=pointer; + } else + addword(&(*s)->liste[i].weiter,t+1,pointer); + return; + } + + ++nodes; + (*s)->n++; + (*s)->liste[i].c=*t; + if (!*t) { + datasize+=strlen((char*)pointer)+1; + (*s)->liste[i].weiter=pointer; + } else { + (*s)->liste[i].weiter=0; + addword(&(*s)->liste[i].weiter,t+1,pointer); + } +} + +void dump(struct letters* s,size_t depth) { + size_t i,j; + if (!s) return; + for (i=0; i<256; ++i) { + if (s->liste[i].c!=i) continue; + for (j=0; j {\n",s->liste[i].c); + if (s->liste[i].c) + dump(s->liste[i].weiter,depth+1); + for (j=0; jn; + assert(usedliste[i].c!=i) { + if (i==0) return; + continue; + } +// printf("marshalhelper: %c\n",i); + x=(unsigned char)s->liste[i].c; + if (!x) { + size_t l=strlen((char*)s->liste[i].weiter)+1; +// puts((char*)s->liste[i].weiter); + x|=useddata<<8; + assert(useddata+l<=datasize); + memcpy(data+useddata,s->liste[i].weiter,l); + useddata+=l; + marshaled[++myindex]=x; + return; + } else { + x|=(used+1)<<8; + marshalhelper(s->liste[i].weiter); + } + marshaled[++myindex]=x; + } +// printf("return\n"); +} + +void marshal(struct letters* s) { + fprintf(stderr,"nodes=%lu, datasize=%lu\n",nodes,datasize); + heap=malloc((nodes+1)*sizeof(uint32_t)+datasize); + if (!heap) return; + marshaled=(uint32_t*)heap; + marshaled[0]=nodes+1; + data=heap+(nodes+1)*sizeof(uint32_t); + marshalhelper(s); + fprintf(stderr,"actually used: %lu nodes, %lu bytes data\n",used,useddata); +} + +char* lookup(char* ds,size_t ofs,const char* t) { + uint32_t* tab=(uint32_t*)ds; + if (ofs>tab[0]) return 0; + while (ofs>8); + else + return lookup(ds,tab[ofs]>>8,t+1); + } else + ++ofs; + if (!ch) break; + } + return NULL; +} + +int main() { + FILE* f=fopen("entities.json","r"); + char buf[256]; + if (!f) return 1; +#if 0 + puts("struct { const char* entity; const char* utf8; } codepoints[] = {"); +#endif + while (fgets(buf,sizeof(buf),f)) { + char* s,* entity; + size_t ul; + if (!isspace(buf[0])) continue; + for (s=buf; *s && *s!='"'; ++s) ; // skip whitespace + if (!*s=='"') continue; + ++s; + entity=s; + if (*entity!='&') continue; ++entity; ++s; + for (; *s && *s!='"'; ++s) ; // skip to end of entity + if (!*s=='"') continue; + if (s[-1]!=';') continue; + s[-1]=0; ++s; + s=strchr(s,'['); + if (!s) continue; + n=0; +#if 0 + printf(" { \"%s\", \"",entity); +#endif + ++s; + *cur=malloc(sizeof(**cur)); + (*cur)->next=0; + if (!((*cur)->entity=strdup(entity))) return 1; + ul=0; + do { + while (isspace(*s)) ++s; + m=scan_ulong(s,&l); + if (!m) return 2; + s+=n; + n=fmt_utf8(tmp,l); + if (ul+n>sizeof((*cur)->utf8)) return 3; + memcpy((*cur)->utf8+ul,tmp,n); + ul+=n; +#if 0 + { + size_t i; + for (i=0; ientity,(*cur)->utf8); + } + fclose(f); +// dump(d,0); + marshal(d); + { + FILE* f=fopen("entities.h","w"); + size_t i; + fprintf(f,"struct {\n uint32_t tab[%lu];\n char data[%lu];\n} entities = {\n {",marshaled[0],datasize); + for (i=0; i '&', '<' -> '<' - * 0 is rejected - * control characters except \t \r \n are written in escaped form - * characters from d780 to dfff and fffe and ffff and everything above 10ffff are also rejected. - * everything else is passed through encoded as UTF-8 */ -size_t fmt_xmlescape(char* dest,uint32_t ch); +/* Marshaling helper functions. + * Escape one character, no matter if it needs escaping or not. + * The functions will reject characters that cannot be represented but + * not characters that the standard says should never occur. The idea + * is to make these functions useful for creating bad encoding for + * penetration testing. + * Depending on the escaping method, the input character (uint32_t, a + * unicode codepoint) may be limited to 0x7f, 0xff or 0x10ffff. */ + +/* XML escaping: '&' -> '&', '<' -> '<', 'ö' -> 'ö' */ +size_t fmt_escapecharxml(char* dest,uint32_t ch); +/* HTML escaping is the same as XML escaping. */ +size_t fmt_escapecharhtml(char* dest,uint32_t ch); + +/* JSON escaping: '\' -> '\\', '"' -> '\"', 'ö' -> '\u00f6' */ +size_t fmt_escapecharjson(char* dest,uint32_t ch); + +/* MIME quoted-printable escaping: 'ö' -> '=f6', characters > 0xff not supported */ +size_t fmt_escapecharquotedprintable(char* dest,uint32_t ch); + +/* MIME quoted-printable escaping with UTF-8: 'ö' -> '=c3=b6', characters > 0x7fffffff not supported */ +size_t fmt_escapecharquotedprintableutf8(char* dest,uint32_t ch); + +/* C escaping: '\' -> '\\', newline -> '\n', 0xc2 -> '\302' */ +size_t fmt_escapecharc(char* dest,uint32_t ch); /* internal functions, may be independently useful */ char fmt_tohex(char c); diff --git a/fmt/fmt_escapecharc.c b/fmt/fmt_escapecharc.c new file mode 100644 index 0000000..887c1f9 --- /dev/null +++ b/fmt/fmt_escapecharc.c @@ -0,0 +1,36 @@ +#include "fmt.h" + +static void fmt_oct3(char* dest,uint8_t w) { + dest[2]=(w&7)+'0'; w>>=3; + dest[1]=(w&7)+'0'; w>>=3; + dest[0]=(w&7)+'0'; +} + +size_t fmt_escapecharc(char* dest,uint32_t ch) { + char c; + if (ch>0xff) return 0; + switch (ch) { + case '\a': c='a'; goto doescape; + case '\b': c='b'; goto doescape; + case 0x1b: c='e'; goto doescape; + case '\f': c='f'; goto doescape; + case '\n': c='n'; goto doescape; + case '\r': c='r'; goto doescape; + case '\t': c='t'; goto doescape; + case '\v': c='v'; goto doescape; + case '\\': + c='\\'; + doescape: + if (dest) { + dest[0]='\\'; + dest[1]=c; + } + return 2; + default: + if (dest) { + dest[0]='\\'; + fmt_oct3(dest+1,ch&0xff); + } + return 4; + } +} diff --git a/fmt/fmt_escapecharhtml.c b/fmt/fmt_escapecharhtml.c new file mode 100644 index 0000000..23e5699 --- /dev/null +++ b/fmt/fmt_escapecharhtml.c @@ -0,0 +1,9 @@ +#ifndef __GNUC__ + +#include "fmt.h" + +size_t fmt_escapecharhtml(char* dest,uint32_t ch) { + return fmt_escapecharxml(dest,ch); +} + +#endif diff --git a/fmt/fmt_escapecharjson.c b/fmt/fmt_escapecharjson.c new file mode 100644 index 0000000..ee7cccd --- /dev/null +++ b/fmt/fmt_escapecharjson.c @@ -0,0 +1,47 @@ +#include "fmt.h" + +static void fmt_hex4(char* dest,uint16_t w) { + dest[3]=fmt_tohex(w&0xf); w>>=4; + dest[2]=fmt_tohex(w&0xf); w>>=4; + dest[1]=fmt_tohex(w&0xf); w>>=4; + dest[0]=fmt_tohex(w&0xf); +} + +size_t fmt_escapecharjson(char* dest,uint32_t ch) { + size_t n; + switch (ch) { + case '\b': + ch='b'; goto simple; + case '\n': + ch='n'; goto simple; + case '\r': + ch='r'; goto simple; + case '"': + case '\\': + case '/': +simple: + if (dest) { + dest[0]='\\'; + dest[1]=ch; + } + return 2; + } + if (ch>0xffff) { + if (ch>0x10ffff) return 0; // highest representable unicode codepoint + if (dest) { + dest[0]='\\'; + dest[1]='u'; + fmt_hex4(dest+2,0xd800 | (((ch-0x10000)>>10)&0x3ff)); + dest+=6; + } + ch=(ch&0x3ff)|0xdc00; + n=6; + } else + n=0; + if (dest) { + dest[0]='\\'; + dest[1]='u'; + fmt_hex4(dest+2,ch); + } + return n+6; +} diff --git a/fmt/fmt_escapecharquotedprintable.c b/fmt/fmt_escapecharquotedprintable.c new file mode 100644 index 0000000..2b07170 --- /dev/null +++ b/fmt/fmt_escapecharquotedprintable.c @@ -0,0 +1,11 @@ +#include "fmt.h" + +size_t fmt_escapecharquotedprintable(char* dest,uint32_t ch) { + if (ch>0xff) return 0; + if (dest) { + dest[0]='='; + dest[2]=fmt_tohex(ch&0xf); ch>>=4; + dest[1]=fmt_tohex(ch&0xf); + } + return 3; +} diff --git a/fmt/fmt_escapecharquotedprintableutf8.c b/fmt/fmt_escapecharquotedprintableutf8.c new file mode 100644 index 0000000..f3d9e86 --- /dev/null +++ b/fmt/fmt_escapecharquotedprintableutf8.c @@ -0,0 +1,10 @@ +#include "fmt.h" + +size_t fmt_escapecharquotedprintableutf8(char* dest,uint32_t ch) { + char buf[FMT_UTF8]; + size_t i,o,j=fmt_utf8(buf,ch); + if (!dest) return j*3; + for (i=o=0; i': s=">"; goto string; + case '\'': s="'"; goto string; + case '"': s="""; goto string; + default: + a[i=fmt_ulong(a,ch)]=0; + b[0]='x'; + b[j=fmt_xlong(b+1,ch)+1]=0; + s=a; + if (i>j) { s=b; i=j; } + if (dest) { + dest[0]='&'; + dest[1]='#'; + byte_copy(dest+2,i,s); + dest[i+2]=';'; + } + return i+3; + } +string: + return fmt_str(dest,s); +} + +#ifdef __GNUC__ +size_t fmt_escapecharhtml(char* dest,uint32_t ch) __attribute__((__alias__("fmt_escapecharxml"))); +#endif diff --git a/test/marshal.c b/test/marshal.c index 870b0d2..8a0f322 100644 --- a/test/marshal.c +++ b/test/marshal.c @@ -104,4 +104,28 @@ int main() { zap(); assert(fmt_asn1dertag(buf,0xc2)==2 && byte_equal(buf,3,"\x81\x42_")); zap(); assert(fmt_strm(buf,"hell","o, worl","d!\n")==14 && byte_equal(buf,15,"hello, world!\n_")); + + assert(fmt_escapecharxml(NULL,0xc2)==6); + zap(); assert(fmt_escapecharxml(buf,0xc2)==6 && byte_equal(buf,7,"Â_")); + assert(fmt_escapecharxml(NULL,0)==4); + zap(); assert(fmt_escapecharxml(buf,0)==4 && byte_equal(buf,5,"�_")); + + assert(fmt_escapecharjson(NULL,'\\')==2); // "\\" + zap(); assert(fmt_escapecharjson(buf,'\\')==2 && byte_equal(buf,3,"\\\\_")); + assert(fmt_escapecharjson(NULL,0xc2)==6); // "\u00c2" + zap(); assert(fmt_escapecharjson(buf,0xc2)==6 && byte_equal(buf,7,"\\u00c2_")); + assert(fmt_escapecharjson(NULL,0x1d11e)==12); // "\ud834\xdd1e" + zap(); assert(fmt_escapecharjson(buf,0x1d11e)==12 && byte_equal(buf,13,"\\ud834\\udd1e_")); + + assert(fmt_escapecharquotedprintable(NULL,'=')==3); // =3d + zap(); assert(fmt_escapecharquotedprintable(buf,'=')==3 && byte_equal(buf,4,"=3d_")); + assert(fmt_escapecharquotedprintable(NULL,0xf6)==3); // =f6 + zap(); assert(fmt_escapecharquotedprintable(buf,0xf6)==3 && byte_equal(buf,4,"=f6_")); + assert(fmt_escapecharquotedprintable(NULL,0x100)==0); + + assert(fmt_escapecharquotedprintableutf8(NULL,'=')==3); // =3d + zap(); assert(fmt_escapecharquotedprintableutf8(buf,'=')==3 && byte_equal(buf,4,"=3d_")); + assert(fmt_escapecharquotedprintableutf8(NULL,0xf6)==6); // =c3=b6 + zap(); assert(fmt_escapecharquotedprintableutf8(buf,0xf6)==6 && byte_equal(buf,7,"=c3=b6_")); + } diff --git a/test/textcode.c b/test/textcode.c index 8b3467d..daefe65 100644 --- a/test/textcode.c +++ b/test/textcode.c @@ -19,5 +19,12 @@ int main() { assert(!array_failed(&a)); write(1,array_start(&a),array_bytes(&a)); write(1,"\n",1); array_trunc(&a); + + strcpy(buf,"Ächt fnördig."); + size_t n; + scan_html(buf,buf,&n); + buf[n]=0; + puts(buf); + return 0; } diff --git a/textcode/fmt_to_array.c b/textcode/fmt_to_array.c index 3853964..ca81cee 100644 --- a/textcode/fmt_to_array.c +++ b/textcode/fmt_to_array.c @@ -4,7 +4,7 @@ void fmt_to_array(size_t (*func)(char*,const char*,size_t), array* a,const char* src,size_t len) { size_t needed=func(0,src,len); - if (array_bytes(a)+needed>needed && + if (array_bytes(a)+needed>=needed && array_allocate(a,1,array_bytes(a)+needed-1)) { char* x=((char*)array_start(a))+array_bytes(a)-needed; func(x,src,len); diff --git a/textcode/scan_html.c b/textcode/scan_html.c index 23d25c0..461cb6d 100644 --- a/textcode/scan_html.c +++ b/textcode/scan_html.c @@ -1,23 +1,63 @@ +#include +#include +#include "entities.h" + #include "fmt.h" #include "textcode.h" #include "haveinline.h" +#include "scan.h" #include "case.h" +#include "str.h" + +static const char* lookup(size_t ofs,const char* t) { + if (ofs>entities.tab[0]) return 0; + while (ofs>8); + else + return lookup(entities.tab[ofs]>>8,t+1); + } else + ++ofs; + if (!ch) break; + } + return NULL; +} size_t scan_html(const char *src,char *dest,size_t *destlen) { register const unsigned char* s=(const unsigned char*) src; size_t written=0,i; for (i=0; s[i]; ++i) { if (s[i]=='&') { - if (case_starts((const char*)s+i+1,"amp;")) { - dest[written]='&'; - i+=4; - } else if (case_starts((const char*)s+i+1,"lt;")) { - dest[written]='<'; - i+=3; - } else if (case_starts((const char*)s+i+1,"gt;")) { - dest[written]='>'; - i+=3; + const char* utf8; + if (s[i+1]=='#') { + unsigned long l; + size_t j; + if ((s[i+2]&~32)=='X') { + j=scan_xlong(src+i+3,&l); + if (!j) j+=3; + } else { + j=scan_ulong(src+i+2,&l); + if (!j) j+=3; + } + if (s[i+j]==';') { + i+=j; + written+=fmt_utf8(dest+written,l); + } else { + dest[written++]='&'; + } + continue; } + utf8=lookup(1,src+i+1); + if (utf8) { + size_t l=strlen(utf8); + memcpy(dest+written,utf8,l); + written+=l; + i+=2+str_chr(src+i+2,';'); + continue; + } else + dest[written]='&'; } else if (s[i]=='<') { if (case_starts((const char*)s+i+1,"br>")) { dest[written]='\n'; diff --git a/tryalloca.c b/tryalloca.c index 388312f..8c705cf 100644 --- a/tryalloca.c +++ b/tryalloca.c @@ -5,6 +5,8 @@ #include #endif -main() { +int main() { char* c=alloca(23); + (void)c; + return 0; } diff --git a/trybsdsf.c b/trybsdsf.c index 27a0529..2808d5a 100644 --- a/trybsdsf.c +++ b/trybsdsf.c @@ -16,4 +16,6 @@ int main() { hdr.headers=v; hdr.hdr_cnt=17; hdr.trailers=v+17; hdr.trl_cnt=23; r=sendfile(0,1,37,42,&hdr,&sbytes,0); + (void)r; + return 0; } diff --git a/tryepoll.c b/tryepoll.c index 6fe7485..ef5f498 100644 --- a/tryepoll.c +++ b/tryepoll.c @@ -1,5 +1,6 @@ #include #include +#include int main() { int efd=epoll_create(10); @@ -9,10 +10,11 @@ int main() { x.data.fd=0; if (epoll_ctl(efd,EPOLL_CTL_ADD,0 /* fd */,&x)==-1) return 111; { - int i,n; + int n; struct epoll_event y[100]; if ((n=epoll_wait(efd,y,100,1000))==-1) return 111; if (n>0) printf("event %d on fd #%d\n",y[0].events,y[0].data.fd); } + return 0; } diff --git a/tryip6.c b/tryip6.c index e0d7cfb..4093b6a 100644 --- a/tryip6.c +++ b/tryip6.c @@ -2,7 +2,9 @@ #include #include -main() { +int main() { struct sockaddr_in6 sa; sa.sin6_family = PF_INET6; + (void)sa; + return 0; } diff --git a/tryn2i.c b/tryn2i.c index 84c3a08..b4f148e 100644 --- a/tryn2i.c +++ b/tryn2i.c @@ -5,4 +5,6 @@ int main() { static char ifname[IFNAMSIZ]; char *tmp=if_indextoname(0,ifname); + (void)tmp; + return 0; } diff --git a/tryscope.c b/tryscope.c index 0b1c139..976bfc3 100644 --- a/tryscope.c +++ b/tryscope.c @@ -2,8 +2,10 @@ #include #include -main() { +int main() { struct sockaddr_in6 sa; sa.sin6_family = PF_INET6; sa.sin6_scope_id = 23; + (void)sa; + return 0; } diff --git a/trysendfile.c b/trysendfile.c index e8555d5..7ec8bfb 100644 --- a/trysendfile.c +++ b/trysendfile.c @@ -55,6 +55,7 @@ int main() { p.trailer_length=6; if (send_file(&destfd,&p,0)>=0) printf("sent %lu bytes.\n",p.bytes_sent); + return 0; } #elif defined(__linux__) @@ -77,6 +78,7 @@ int main() { off_t r=sendfile(1,fd,&o,23); if (r!=-1) printf("sent %llu bytes.\n",r); + return 0; } #else diff --git a/trysigio.c b/trysigio.c index 5523ba3..b0d8fa3 100644 --- a/trysigio.c +++ b/trysigio.c @@ -3,6 +3,7 @@ #include #include #include +#include int main() { int signum=SIGRTMIN+1; @@ -36,4 +37,5 @@ int main() { } } } + return 0; } diff --git a/trysl.c b/trysl.c index a617b24..4dce3be 100644 --- a/trysl.c +++ b/trysl.c @@ -7,6 +7,8 @@ #include #endif -main() { +int main() { socklen_t t; + (void)t; + return 0; } diff --git a/trysocket.c b/trysocket.c index 8623452..f7324ae 100644 --- a/trysocket.c +++ b/trysocket.c @@ -2,6 +2,8 @@ #include #include -main() { +int main() { int fd=socket(PF_INET,SOCK_STREAM,IPPROTO_TCP); + (int)fd; + return 0; }