/* * U funkce join_urls musi byt prvni url absolutni (takove, co projde funkci * parse_url bez chyby --- pokud neni absolutni, tak to spatne na internal) a * druhe url je relativni cesta vuci nemu nebo taky absolutni url. Pokud je * druhe url absolutni, vrati se to; pokud je relativni, tak se spoji prvni a * druhe url. */ unsigned char *join_urls(unsigned char *base, unsigned char *rel) { unsigned char *p, *n, *pp, *ch; int l; int lo = !casecmp(base, cast_uchar "file://", 7); int data = !casecmp(base, cast_uchar "data:", 5); if (rel[0] == '#' || !rel[0]) { n = stracpy(base); for (p = n; *p && *p != POST_CHAR && *p != '#'; p++) ; *p = 0; add_to_strn(&n, rel); goto return_n; } if (rel[0] == '?' || rel[0] == '&') { unsigned char rj[3]; unsigned char *d = get_url_data(base); if (!d) goto bad_base; rj[0] = rel[0]; rj[1] = POST_CHAR; rj[2] = 0; d += strcspn(cast_const_char d, cast_const_char rj); n = memacpy(base, d - base); add_to_strn(&n, rel); goto return_n; } if (rel[0] == '/' && rel[1] == '/' && !data) { unsigned char *s; if (!(s = cast_uchar strstr(cast_const_char base, "//"))) { if (!(s = cast_uchar strchr(cast_const_char base, ':'))) { bad_base: internal("bad base url: %s", base); return NULL; } s++; } n = memacpy(base, s - base); add_to_strn(&n, rel); if (!parse_url(n, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL)) goto return_n; add_to_strn(&n, cast_uchar "/"); if (!parse_url(n, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL)) goto return_n; mem_free(n); } if (!casecmp(cast_uchar "proxy://", rel, 8)) goto prx; if (!parse_url(rel, &l, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL)) { n = stracpy(rel); goto return_n; } n = stracpy(rel); while (n[0] && n[strlen(cast_const_char n) - 1] <= ' ') n[strlen(cast_const_char n) - 1] = 0; extend_str(&n, 1); ch = cast_uchar strrchr(cast_const_char n, '#'); if (!ch || strchr(cast_const_char ch, '/')) ch = n + strlen(cast_const_char n); memmove(ch + 1, ch, strlen(cast_const_char ch) + 1); *ch = '/'; if (!parse_url(n, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL)) goto return_n; mem_free(n); prx: if (parse_url(base, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, &p, NULL, NULL) || !p) { goto bad_base; } if (!dsep(*p)) p--; if (!data) { if (end_of_dir(base, rel[0])) for (; *p; p++) { if (end_of_dir(base, *p)) break; } else if (!dsep(rel[0])) for (pp = p; *pp; pp++) { if (end_of_dir(base, *pp)) break; if (dsep(*pp)) p = pp + 1; } } n = memacpy(base, p - base); add_to_strn(&n, rel); goto return_n; return_n: extend_str(&n, 1); translate_directories(n); return n; }
/*-----------------------------------------------------------------------------------*/ static u16_t parse_headers(u16_t len) { char *cptr; static unsigned char i; while(len > 0 && s.httpheaderlineptr < sizeof(s.httpheaderline)) { s.httpheaderline[s.httpheaderlineptr] = *(char *)uip_appdata; uip_appdata = (char *)uip_appdata + 1; --len; if(s.httpheaderline[s.httpheaderlineptr] == ISO_nl) { /* We have an entire HTTP header line in s.httpheaderline, so we parse it. */ if(s.httpheaderline[0] == ISO_cr) { /* This was the last header line (i.e., and empty "\r\n"), so we are done with the headers and proceed with the actual data. */ s.state = WEBCLIENT_STATE_DATA; return len; } s.httpheaderline[s.httpheaderlineptr - 1] = 0; /* Check for specific HTTP header fields. */ if(casecmp(s.httpheaderline, http_content_type, sizeof(http_content_type) - 1) == 0) { /* Found Content-type field. */ cptr = strchr(s.httpheaderline, ';'); if(cptr != NULL) { *cptr = 0; } strncpy(s.mimetype, s.httpheaderline + sizeof(http_content_type) - 1, sizeof(s.mimetype)); } else if(casecmp(s.httpheaderline, http_location, sizeof(http_location) - 1) == 0) { cptr = s.httpheaderline + sizeof(http_location) - 1; if(strncmp(cptr, http_http, 7) == 0) { cptr += 7; for(i = 0; i < s.httpheaderlineptr - 7; ++i) { if(*cptr == 0 || *cptr == '/' || *cptr == ' ' || *cptr == ':') { s.host[i] = 0; break; } s.host[i] = *cptr; ++cptr; } } strncpy(s.file, cptr, sizeof(s.file)); /* s.file[s.httpheaderlineptr - i] = 0;*/ } /* We're done parsing, so we reset the pointer and start the next line. */ s.httpheaderlineptr = 0; } else { ++s.httpheaderlineptr; } } return len; }
unsigned char *translate_url(unsigned char *url, unsigned char *cwd) { unsigned char *ch; unsigned char *nu, *da; unsigned char *prefix; int sl; while (*url == ' ') url++; if (*url && url[strlen(cast_const_char url) - 1] == ' ') { nu = stracpy(url); while (*nu && nu[strlen(cast_const_char nu) - 1] == ' ') nu[strlen(cast_const_char nu) - 1] = 0; ch = translate_url(nu, cwd); mem_free(nu); return ch; } if (!casecmp(cast_uchar "proxy://", url, 8)) return NULL; if (!parse_url(url, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, &da, NULL, NULL)) { nu = stracpy(url); goto return_nu; } if (strchr(cast_const_char url, POST_CHAR)) return NULL; if (strstr(cast_const_char url, "://")) { nu = stracpy(url); extend_str(&nu, 1); ch = cast_uchar strrchr(cast_const_char nu, '#'); if (!ch || strchr(cast_const_char ch, '/')) ch = nu + strlen(cast_const_char nu); memmove(ch + 1, ch, strlen(cast_const_char ch) + 1); *ch = '/'; if (!parse_url(nu, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL)) goto return_nu; mem_free(nu); } prefix = cast_uchar "file://"; if (url[0] == '[' && strchr(cast_const_char url, ']')) { ch = url; goto http; } ch = url + strcspn(cast_const_char url, ".:/@"); sl = 0; #ifdef SPAD if (strchr(cast_const_char url, ':') && _is_local(cast_const_char url)) goto set_prefix; #endif if (*ch != ':' || *(url + strcspn(cast_const_char url, "/@")) == '@') { if (*url != '.' && *ch == '.') { unsigned char *f, *e; int i; for (e = ch + 1; *(f = e + strcspn(cast_const_char e, ".:/")) == '.'; e = f + 1) ; for (i = 0; i < f - e; i++) if (e[i] < '0' || e[i] > '9') goto noip; goto http; noip: if (f - e == 2 && casecmp(e, cast_uchar "gz", 2)) { http: prefix = cast_uchar "http://", sl = 1; } else { char *tld[] = { "com", "edu", "net", "org", "gov", "mil", "int", "arpa", "aero", "biz", "coop", "info", "museum", "name", "pro", "cat", "jobs", "mobi", "travel", "tel", "onion", "exit", NULL }; for (i = 0; tld[i]; i++) if ((size_t)(f - e) == strlen(cast_const_char tld[i]) && !casecmp(cast_uchar tld[i], e, f - e)) goto http; } } if (*ch == '@' || *ch == ':' || !cmpbeg(url, cast_uchar "ftp.")) prefix = cast_uchar "ftp://", sl = 1; goto set_prefix; set_prefix: nu = stracpy(prefix); add_to_strn(&nu, url); if (sl && !strchr(cast_const_char url, '/')) add_to_strn(&nu, cast_uchar "/"); if (parse_url(nu, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL)) { mem_free(nu); return NULL; } goto return_nu; } #ifdef DOS_FS if (ch == url + 1) goto set_prefix; #endif if (!(nu = memacpy(url, ch - url + 1))) return NULL; add_to_strn(&nu, cast_uchar "//"); add_to_strn(&nu, ch + 1); if (!parse_url(nu, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL)) goto return_nu; add_to_strn(&nu, cast_uchar "/"); if (!parse_url(nu, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL)) goto return_nu; mem_free(nu); return NULL; return_nu: insert_wd(&nu, cwd); extend_str(&nu, 1); translate_directories(nu); nu = translate_hashbang(nu); return nu; }
void http_got_header(struct connection *c, struct read_buffer *rb) { int cf; int state = c->state != S_PROC ? S_GETH : S_PROC; unsigned char *head; unsigned char *cookie, *ch; int a, h, version; unsigned char *d; struct cache_entry *e; struct http_connection_info *info; unsigned char *host = upcase(c->url[0]) != 'P' ? c->url : get_url_data(c->url); set_timeout(c); info = c->info; if (rb->close == 2) { unsigned char *h; if (!c->tries && (h = get_host_name(host))) { if (info->bl_flags & BL_NO_CHARSET) { del_blacklist_entry(h, BL_NO_CHARSET); } else { add_blacklist_entry(h, BL_NO_CHARSET); c->tries = -1; } mem_free(h); } setcstate(c, S_CANT_READ); retry_connection(c); return; } rb->close = 0; again: if ((a = get_header(rb)) == -1) { setcstate(c, S_HTTP_ERROR); abort_connection(c); return; } if (!a) { read_from_socket(c, c->sock1, rb, http_got_header); setcstate(c, state); return; } if (a != -2) { head = mem_alloc(a + 1); memcpy(head, rb->data, a); head[a] = 0; kill_buffer_data(rb, a); } else { head = stracpy("HTTP/0.9 200 OK\r\nContent-Type: text/html\r\n\r\n"); } if (get_http_code(head, &h, &version) || h == 101) { mem_free(head); setcstate(c, S_HTTP_ERROR); abort_connection(c); return; } if (check_http_server_bugs(host, c->info, head) && is_connection_restartable(c)) { mem_free(head); setcstate(c, S_RESTART); retry_connection(c); return; } ch = head; while ((cookie = parse_http_header(ch, "Set-Cookie", &ch))) { unsigned char *host = upcase(c->url[0]) != 'P' ? c->url : get_url_data(c->url); set_cookie(NULL, host, cookie); mem_free(cookie); } if (h == 100) { mem_free(head); state = S_PROC; goto again; } if (h < 200) { mem_free(head); setcstate(c, S_HTTP_ERROR); abort_connection(c); return; } if (h == 204) { mem_free(head); setcstate(c, S_HTTP_204); http_end_request(c, 0); return; } if (h == 304) { mem_free(head); setcstate(c, S_OK); http_end_request(c, 1); return; } if ((h == 500 || h == 502 || h == 503 || h == 504) && http_bugs.retry_internal_errors && is_connection_restartable(c)) { /* !!! FIXME: wait some time ... */ mem_free(head); setcstate(c, S_RESTART); retry_connection(c); return; } if (!c->cache && get_cache_entry(c->url, &c->cache)) { mem_free(head); setcstate(c, S_OUT_OF_MEM); abort_connection(c); return; } e = c->cache; e->http_code = h; if (e->head) mem_free(e->head); e->head = head; if ((d = parse_http_header(head, "Expires", NULL))) { time_t t = parse_http_date(d); if (t && e->expire_time != 1) e->expire_time = t; mem_free(d); } if ((d = parse_http_header(head, "Pragma", NULL))) { if (!casecmp(d, "no-cache", 8)) e->expire_time = 1; mem_free(d); } if ((d = parse_http_header(head, "Cache-Control", NULL))) { char *f = d; while (1) { while (*f && (*f == ' ' || *f == ',')) f++; if (!*f) break; if (!casecmp(f, "no-cache", 8) || !casecmp(f, "must-revalidate", 15)) { e->expire_time = 1; } if (!casecmp(f, "max-age=", 8)) { if (e->expire_time != 1) e->expire_time = time(NULL) + atoi(f + 8); } while (*f && *f != ',') f++; } mem_free(d); } #ifdef HAVE_SSL if (c->ssl) { int l = 0; if (e->ssl_info) mem_free(e->ssl_info); e->ssl_info = init_str(); add_num_to_str(&e->ssl_info, &l, SSL_get_cipher_bits(c->ssl, NULL)); add_to_str(&e->ssl_info, &l, "-bit "); add_to_str(&e->ssl_info, &l, SSL_get_cipher_version(c->ssl)); add_to_str(&e->ssl_info, &l, " "); add_to_str(&e->ssl_info, &l, (unsigned char *)SSL_get_cipher_name(c->ssl)); } #endif if (e->redirect) mem_free(e->redirect), e->redirect = NULL; if (h == 301 || h == 302 || h == 303 || h == 307) { if ((h == 302 || h == 307) && !e->expire_time) e->expire_time = 1; if ((d = parse_http_header(e->head, "Location", NULL))) { unsigned char *user, *ins; unsigned char *newuser, *newpassword; if (!parse_url(d, NULL, &user, NULL, NULL, NULL, &ins, NULL, NULL, NULL, NULL, NULL, NULL) && !user && ins && (newuser = get_user_name(host))) { if (*newuser) { int ins_off = ins - d; newpassword = get_pass(host); if (!newpassword) newpassword = stracpy(""); add_to_strn(&newuser, ":"); add_to_strn(&newuser, newpassword); add_to_strn(&newuser, "@"); extend_str(&d, strlen(newuser)); ins = d + ins_off; memmove(ins + strlen(newuser), ins, strlen(ins) + 1); memcpy(ins, newuser, strlen(newuser)); mem_free(newpassword); } mem_free(newuser); } if (e->redirect) mem_free(e->redirect); e->redirect = d; e->redirect_get = h == 303; } } if (!e->expire_time && strchr(c->url, POST_CHAR)) e->expire_time = 1; info->close = 0; info->length = -1; info->version = version; if ((d = parse_http_header(e->head, "Connection", NULL)) || (d = parse_http_header(e->head, "Proxy-Connection", NULL))) { if (!strcasecmp(d, "close")) info->close = 1; mem_free(d); } else if (version < 11) info->close = 1; cf = c->from; c->from = 0; if ((d = parse_http_header(e->head, "Content-Range", NULL))) { if (strlen(d) > 6) { d[5] = 0; if (!(strcasecmp(d, "bytes")) && d[6] >= '0' && d[6] <= '9') { #if defined(HAVE_STRTOLL) long long f = strtoll(d + 6, NULL, 10); #elif defined(HAVE_STRTOQ) longlong f = strtoq(d + 6, NULL, 10); #else long f = strtol(d + 6, NULL, 10); if (f == MAXLONG) f = -1; #endif if (f >= 0 && (off_t)f >= 0 && (off_t)f == f) c->from = f; } } mem_free(d); } if (cf && !c->from && !c->unrestartable) c->unrestartable = 1; if (c->from > cf || c->from < 0) { setcstate(c, S_HTTP_ERROR); abort_connection(c); return; } if ((d = parse_http_header(e->head, "Content-Length", NULL))) { unsigned char *ep; #if defined(HAVE_STRTOLL) long long l = strtoll(d, (char **)(void *)&ep, 10); #elif defined(HAVE_STRTOQ) longlong l = strtoq(d, (char **)(void *)&ep, 10); #else long l = strtol(d, (char **)(void *)&ep, 10); if (l == MAXLONG) l = -1; #endif if (!*ep && l >= 0 && (off_t)l >= 0 && (off_t)l == l) { if (!info->close || version >= 11) info->length = l; if (c->from + l >= 0) c->est_length = c->from + l; } mem_free(d); } if ((d = parse_http_header(e->head, "Accept-Ranges", NULL))) { if (!strcasecmp(d, "none") && !c->unrestartable) c->unrestartable = 1; mem_free(d); } else { if (!c->unrestartable && !c->from) c->unrestartable = 1; } if (info->bl_flags & BL_NO_RANGE && !c->unrestartable) c->unrestartable = 1; if ((d = parse_http_header(e->head, "Transfer-Encoding", NULL))) { if (!strcasecmp(d, "chunked")) { info->length = -2; info->chunk_remaining = -1; } mem_free(d); } if (!info->close && info->length == -1) info->close = 1; if ((d = parse_http_header(e->head, "Last-Modified", NULL))) { if (e->last_modified && strcasecmp(e->last_modified, d)) { delete_entry_content(e); if (c->from) { c->from = 0; mem_free(d); setcstate(c, S_MODIFIED); retry_connection(c); return; } } if (!e->last_modified) e->last_modified = d; else mem_free(d); } if (!e->last_modified && (d = parse_http_header(e->head, "Date", NULL))) e->last_modified = d; if (info->length == -1 || (version < 11 && info->close)) rb->close = 1; read_http_data(c, rb); }
struct table *parse_table(unsigned char *html, unsigned char *eof, unsigned char **end, struct rgb *bgcolor, int sh, struct s_e **bad_html, int *bhp) { int qqq; struct table *t; struct table_cell *cell; unsigned char *t_name, *t_attr, *en; int t_namelen; int x = 0, y = -1; int p = 0; unsigned char *lbhp = NULL; int l_al = AL_LEFT; int l_val = VAL_MIDDLE; int csp, rsp; int group = 0; int i, j, k; struct rgb l_col; int c_al = AL_TR, c_val = VAL_TR, c_width = W_AUTO, c_span = 0; memcpy(&l_col, bgcolor, sizeof(struct rgb)); *end = html; if (bad_html) { *bad_html = DUMMY; *bhp = 0; } if (!(t = new_table())) return NULL; se: en = html; see: html = en; if (bad_html && !p && !lbhp) { if (!(*bhp & (ALLOC_GR-1))) { if ((unsigned)*bhp > MAXINT / sizeof(struct s_e) - ALLOC_GR) overalloc(); *bad_html = mem_realloc(*bad_html, (*bhp + ALLOC_GR) * sizeof(struct s_e)); } lbhp = (*bad_html)[(*bhp)++].s = html; } while (html < eof && *html != '<') html++; if (html >= eof) { if (p) CELL(t, x, y)->end = html; if (lbhp) (*bad_html)[*bhp-1].e = html; goto scan_done; } if (html + 2 <= eof && (html[1] == '!' || html[1] == '?')) { html = skip_comment(html, eof); goto se; } if (parse_element(html, eof, &t_name, &t_namelen, &t_attr, &en)) { html++; goto se; } if (t_namelen == 5 && !casecmp(t_name, "TABLE", 5)) { en = skip_table(en, eof); goto see; } if (t_namelen == 6 && !casecmp(t_name, "/TABLE", 6)) { if (c_span) new_columns(t, c_span, c_width, c_al, c_val, 1); if (p) CELL(t, x, y)->end = html; if (lbhp) (*bad_html)[*bhp-1].e = html; goto scan_done; } if (t_namelen == 8 && !casecmp(t_name, "COLGROUP", 8)) { if (c_span) new_columns(t, c_span, c_width, c_al, c_val, 1); if (lbhp) (*bad_html)[*bhp-1].e = html, lbhp = NULL; c_al = AL_TR; c_val = VAL_TR; c_width = W_AUTO; get_align(t_attr, &c_al); get_valign(t_attr, &c_val); get_c_width(t_attr, &c_width, sh); if ((c_span = get_num(t_attr, "span")) == -1) c_span = 1; goto see; } if (t_namelen == 9 && !casecmp(t_name, "/COLGROUP", 9)) { if (c_span) new_columns(t, c_span, c_width, c_al, c_val, 1); if (lbhp) (*bad_html)[*bhp-1].e = html, lbhp = NULL; c_span = 0; c_al = AL_TR; c_val = VAL_TR; c_width = W_AUTO; goto see; } if (t_namelen == 3 && !casecmp(t_name, "COL", 3)) { int sp, wi, al, val; if (lbhp) (*bad_html)[*bhp-1].e = html, lbhp = NULL; if ((sp = get_num(t_attr, "span")) == -1) sp = 1; wi = c_width; al = c_al; val = c_val; get_align(t_attr, &al); get_valign(t_attr, &val); get_c_width(t_attr, &wi, sh); new_columns(t, sp, wi, al, val, !!c_span); c_span = 0; goto see; } if (t_namelen == 3 && (!casecmp(t_name, "/TR", 3) || !casecmp(t_name, "/TD", 3) || !casecmp(t_name, "/TH", 3))) { if (c_span) new_columns(t, c_span, c_width, c_al, c_val, 1); if (p) CELL(t, x, y)->end = html, p = 0; if (lbhp) (*bad_html)[*bhp-1].e = html, lbhp = NULL; } if (t_namelen == 2 && !casecmp(t_name, "TR", 2)) { if (c_span) new_columns(t, c_span, c_width, c_al, c_val, 1); if (p) CELL(t, x, y)->end = html, p = 0; if (lbhp) (*bad_html)[*bhp-1].e = html, lbhp = NULL; if (group) group--; l_al = AL_LEFT; l_val = VAL_MIDDLE; memcpy(&l_col, bgcolor, sizeof(struct rgb)); get_align(t_attr, &l_al); get_valign(t_attr, &l_val); get_bgcolor(t_attr, &l_col); y++, x = 0; goto see; } if (t_namelen == 5 && ((!casecmp(t_name, "THEAD", 5)) || (!casecmp(t_name, "TBODY", 5)) || (!casecmp(t_name, "TFOOT", 5)))) { if (c_span) new_columns(t, c_span, c_width, c_al, c_val, 1); if (lbhp) (*bad_html)[*bhp-1].e = html, lbhp = NULL; group = 2; } if (t_namelen != 2 || (casecmp(t_name, "TD", 2) && casecmp(t_name, "TH", 2))) goto see; if (c_span) new_columns(t, c_span, c_width, c_al, c_val, 1); if (lbhp) (*bad_html)[*bhp-1].e = html, lbhp = NULL; if (p) CELL(t, x, y)->end = html, p = 0; if (y == -1) y = 0, x = 0; nc: cell = new_cell(t, x, y); if (cell->used) { if (cell->colspan == -1) goto see; x++; goto nc; } cell->mx = x; cell->my = y; cell->used = 1; cell->start = en; p = 1; cell->align = l_al; cell->valign = l_val; if ((cell->b = upcase(t_name[1]) == 'H')) cell->align = AL_CENTER; if (group == 1) cell->group = 1; if (x < t->c) { if (t->cols[x].align != AL_TR) cell->align = t->cols[x].align; if (t->cols[x].valign != VAL_TR) cell->valign = t->cols[x].valign; } memcpy(&cell->bgcolor, &l_col, sizeof(struct rgb)); get_align(t_attr, &cell->align); get_valign(t_attr, &cell->valign); get_bgcolor(t_attr, &cell->bgcolor); if ((csp = get_num(t_attr, "colspan")) == -1) csp = 1; if (!csp) csp = -1; if ((rsp = get_num(t_attr, "rowspan")) == -1) rsp = 1; if (!rsp) rsp = -1; if (csp >= 0 && rsp >= 0 && csp * rsp > 100000) { if (csp > 10) csp = -1; if (rsp > 10) rsp = -1; } cell->colspan = csp; cell->rowspan = rsp; if (csp == 1) { int w = W_AUTO; get_c_width(t_attr, &w, sh); if (w != W_AUTO) set_td_width(t, x, w, 0); } qqq = t->x; for (i = 1; csp != -1 ? i < csp : x + i < qqq; i++) { struct table_cell *sc = new_cell(t, x + i, y); if (sc->used) { csp = i; for (k = 0; k < i; k++) CELL(t, x + k, y)->colspan = csp; break; } sc->used = sc->spanned = 1; sc->rowspan = rsp; sc->colspan = csp; sc->mx = x; sc->my = y; } qqq = t->y; for (j = 1; rsp != -1 ? j < rsp : y + j < qqq; j++) { for (k = 0; k < i; k++) { struct table_cell *sc = new_cell(t, x + k, y + j); if (sc->used) { int l, m; if (sc->mx == x && sc->my == y) continue; /*internal("boo");*/ for (l = 0; l < k; l++) memset(CELL(t, x + l, y + j), 0, sizeof(struct table_cell)); rsp = j; for (l = 0; l < i; l++) for (m = 0; m < j; m++) CELL(t, x + l, y + m)->rowspan = j; goto brk; } sc->used = sc->spanned = 1; sc->rowspan = rsp; sc->colspan = csp; sc->mx = x; sc->my = y; } } brk: goto see; scan_done: *end = html; for (x = 0; x < t->x; x++) for (y = 0; y < t->y; y++) { struct table_cell *c = CELL(t, x, y); if (!c->spanned) { if (c->colspan == -1) c->colspan = t->x - x; if (c->rowspan == -1) c->rowspan = t->y - y; } } if ((unsigned)t->y > MAXINT / sizeof(int)) overalloc(); t->r_heights = mem_alloc(t->y * sizeof(int)); memset(t->r_heights, 0, t->y * sizeof(int)); for (x = 0; x < t->c; x++) if (t->cols[x].width != W_AUTO) set_td_width(t, x, t->cols[x].width, 1); set_td_width(t, t->x, W_AUTO, 0); return t; }
int main(int argc, char* argv[]) { if (argc < 4 || argc > 6) { std::cout << "Usage: embedfile [-wx] [-text] <inout> <output> <fieldname>" << std::endl; return error_invalidargs; } bool wxWidgets_image = false; bool text_content = false; int argc_offset = 1; if (casecmp(argv[argc_offset], "-wx")) { wxWidgets_image = true; argc_offset++; } if (casecmp(argv[argc_offset], "-text")) { text_content = true; argc_offset++; } std::string input_file(argv[argc_offset]); std::string output_basename(argv[argc_offset + 1]); std::string field_name(argv[argc_offset + 2]); std::ios::openmode mode = std::ios::in; if (!text_content) { mode |= std::ios::binary; } std::ifstream file_in(input_file.c_str(), mode); if (file_in.bad()) { std::cout << "ERROR: Error opening input file: " << input_file << std::endl; return error_cantopenfile; } // Get the size of the input stream size_t input_size; file_in.seekg(0, std::ios::end); if ((int) file_in.tellg() != -1) { input_size = (size_t) file_in.tellg(); } else { std::cout << "ERROR: Failed to get size of input file: " << input_file << std::endl; file_in.close(); return error_ioerror; } file_in.seekg(0, std::ios::beg); // Generates two files, one header and one source file std::string headerName = output_basename + ".h"; std::string sourceName = output_basename + ".cpp"; std::ofstream source_out(sourceName.c_str()); if (source_out.bad()) { std::cout << "ERROR: Error opening output file: " << sourceName << std::endl; return error_cantoutputfile; } std::ofstream header_out(headerName.c_str()); if (header_out.bad()) { std::cout << "ERROR: Error opening output file: " << headerName << std::endl; return error_cantoutputfile; } if (text_content) { do_text_content(file_in, source_out, field_name, input_size); } else { do_binary_content(file_in, source_out, field_name, input_size, wxWidgets_image); } write_header(header_out, field_name, text_content, wxWidgets_image); file_in.close(); source_out.close(); header_out.close(); return error_none; }