Merge branch 'bug/win64gc'

Conflicts:
	istream.c
	main.c
This commit is contained in:
Tatsuya Kinoshita
2013-10-14 23:02:26 +09:00
13 changed files with 441 additions and 181 deletions
+4
View File
@@ -210,6 +210,10 @@ typedef RETSIGTYPE MySignalHandler;
#define SUPPORT_WIN9X_CONSOLE_MBCS 1
#endif
#if defined(__CYGWIN__) && defined(__x86_64__)
#define DONT_CALL_GC_AFTER_FORK
#endif
#if defined(__DJGPP__)
#define DEFAULT_TERM "dosansi"
#else
+33 -25
View File
@@ -677,6 +677,7 @@ readHeader(URLFile *uf, Buffer *newBuf, int thru, ParsedURL *pu)
#endif
init_stream(&f, SCM_LOCAL, newStrStream(src));
loadHTMLstream(&f, newBuf, NULL, TRUE);
UFclose(&f);
for (l = newBuf->lastLine; l && l->real_linenumber;
l = l->prev)
l->real_linenumber = 0;
@@ -7238,16 +7239,17 @@ loadHTMLString(Str page)
MySignalHandler(*volatile prevtrap) (SIGNAL_ARG) = NULL;
Buffer *newBuf;
init_stream(&f, SCM_LOCAL, newStrStream(page));
newBuf = newBuffer(INIT_BUFFER_WIDTH);
if (SETJMP(AbortLoading) != 0) {
TRAP_OFF;
discardBuffer(newBuf);
UFclose(&f);
return NULL;
}
TRAP_ON;
init_stream(&f, SCM_LOCAL, newStrStream(page));
#ifdef USE_M17N
newBuf->document_charset = InnerCharset;
#endif
@@ -7257,6 +7259,7 @@ loadHTMLString(Str page)
#endif
TRAP_OFF;
UFclose(&f);
newBuf->topLine = newBuf->firstLine;
newBuf->lastLine = newBuf->currentLine;
newBuf->currentLine = newBuf->firstLine;
@@ -7486,15 +7489,13 @@ loadImageBuffer(URLFile *uf, Buffer *newBuf)
!stat(cache->file, &st))
goto image_buffer;
TRAP_ON;
if (IStype(uf->stream) != IST_ENCODED)
uf->stream = newEncodedStream(uf->stream, uf->encoding);
TRAP_ON;
if (save2tmp(*uf, cache->file) < 0) {
UFclose(uf);
TRAP_OFF;
return NULL;
}
UFclose(uf);
TRAP_OFF;
cache->loaded = IMG_FLAG_LOADED;
@@ -7514,6 +7515,7 @@ loadImageBuffer(URLFile *uf, Buffer *newBuf)
init_stream(&f, SCM_LOCAL, newStrStream(tmp));
loadHTMLstream(&f, newBuf, src, TRUE);
UFclose(&f);
if (src)
fclose(src);
@@ -7909,6 +7911,8 @@ save2tmp(URLFile uf, char *tmpf)
clen_t linelen = 0, trbyte = 0;
MySignalHandler(*volatile prevtrap) (SIGNAL_ARG) = NULL;
static JMP_BUF env_bak;
volatile int retval = 0;
char *volatile buf = NULL;
ff = fopen(tmpf, "wb");
if (ff == NULL) {
@@ -7945,25 +7949,25 @@ save2tmp(URLFile uf, char *tmpf)
else
#endif /* USE_NNTP */
{
Str buf = Strnew_size(SAVE_BUF_SIZE);
while (UFread(&uf, buf, SAVE_BUF_SIZE)) {
if (Strfputs(buf, ff) != buf->length) {
bcopy(env_bak, AbortLoading, sizeof(JMP_BUF));
TRAP_OFF;
fclose(ff);
current_content_length = 0;
return -2;
int count;
buf = NewWithoutGC_N(char, SAVE_BUF_SIZE);
while ((count = ISread_n(uf.stream, buf, SAVE_BUF_SIZE)) > 0) {
if (fwrite(buf, 1, count, ff) != count) {
retval = -2;
goto _end;
}
linelen += buf->length;
linelen += count;
showProgress(&linelen, &trbyte);
}
}
_end:
bcopy(env_bak, AbortLoading, sizeof(JMP_BUF));
TRAP_OFF;
xfree(buf);
fclose(ff);
current_content_length = 0;
return 0;
return retval;
}
Buffer *
@@ -8074,7 +8078,8 @@ _MoveFile(char *path1, char *path2)
FILE *f2;
int is_pipe;
clen_t linelen = 0, trbyte = 0;
Str buf;
char *buf = NULL;
int count;
f1 = openIS(path1);
if (f1 == NULL)
@@ -8092,12 +8097,13 @@ _MoveFile(char *path1, char *path2)
return -1;
}
current_content_length = 0;
buf = Strnew_size(SAVE_BUF_SIZE);
while (ISread(f1, buf, SAVE_BUF_SIZE)) {
Strfputs(buf, f2);
linelen += buf->length;
buf = NewWithoutGC_N(char, SAVE_BUF_SIZE);
while ((count = ISread_n(f1, buf, SAVE_BUF_SIZE)) > 0) {
fwrite(buf, 1, count, f2);
linelen += count;
showProgress(&linelen, &trbyte);
}
xfree(buf);
ISclose(f1);
if (is_pipe)
pclose(f2);
@@ -8456,21 +8462,23 @@ uncompress_stream(URLFile *uf, char **src)
}
if (pid2 == 0) {
/* child2 */
Str buf = Strnew_size(SAVE_BUF_SIZE);
char *buf = NewWithoutGC_N(char, SAVE_BUF_SIZE);
int count;
FILE *f = NULL;
setup_child(TRUE, 2, UFfileno(uf));
if (tmpf)
f = fopen(tmpf, "wb");
while (UFread(uf, buf, SAVE_BUF_SIZE)) {
if (Strfputs(buf, stdout) < 0)
while ((count = ISread_n(uf->stream, buf, SAVE_BUF_SIZE)) > 0) {
if (fwrite(buf, 1, count, stdout) != count)
break;
if (f && fwrite(buf, 1, count, f) != count)
break;
if (f)
Strfputs(buf, f);
}
UFclose(uf);
if (f)
fclose(f);
xfree(buf);
exit(0);
}
/* child1 */
+4 -2
View File
@@ -76,6 +76,7 @@ typedef int wc_ces; /* XXX: not used */
#include "textlist.h"
#include "funcname1.h"
#include "terms.h"
#include "istream.h"
#ifndef HAVE_BCOPY
void bcopy(const void *, void *, int);
@@ -288,8 +289,6 @@ extern int REV_LB[];
#define inputFilenameHist(p,d,h) inputLineHist(p,d,IN_FILENAME,h)
#define inputChar(p) inputLine(p,"",IN_CHAR)
#define free(x) GC_free(x) /* let GC do it. */
#ifdef __EMX__
#define HAVE_STRCASECMP
#define strcasecmp stricmp
@@ -895,6 +894,9 @@ global char *index_file init(NULL);
global char *CurrentDir;
global int CurrentPid;
#if defined(DONT_CALL_GC_AFTER_FORK) && defined(USE_IMAGE)
global char *MyProgramName init("w3m");
#endif /* defined(DONT_CALL_GC_AFTER_FORK) && defined(USE_IMAGE) */
/*
* global Buffer *Currentbuf;
* global Buffer *Firstbuf;
+3 -4
View File
@@ -1,19 +1,17 @@
/* $Id: html.h,v 1.31 2010/08/14 01:29:40 htrb Exp $ */
#ifndef _HTML_H
#define _HTML_H
#include "config.h"
#ifdef USE_SSL
#include <openssl/bio.h>
#include <openssl/x509.h>
#include <openssl/ssl.h>
#endif /* USE_SSL */
#include "istream.h"
#define StrUFgets(f) StrISgets((f)->stream)
#define StrmyUFgets(f) StrmyISgets((f)->stream)
#define UFgetc(f) ISgetc((f)->stream)
#define UFundogetc(f) ISundogetc((f)->stream)
#define UFread(f,buf,len) ISread((f)->stream,buf,len)
#define UFclose(f) (void)(ISclose((f)->stream) == 0 && ((f)->stream = NULL))
#define UFfileno(f) ISfileno((f)->stream)
@@ -62,11 +60,12 @@ typedef struct _ParsedURL {
int is_nocache;
} ParsedURL;
union input_stream;
typedef struct {
unsigned char scheme;
char is_cgi;
char encoding;
InputStream stream;
union input_stream *stream;
char *ext;
int compression;
int content_encoding;
+28 -5
View File
@@ -90,17 +90,18 @@ termImage()
static int
openImgdisplay()
{
char *cmd;
if (!strchr(Imgdisplay, '/'))
cmd = Strnew_m_charp(w3m_auxbin_dir(), "/", Imgdisplay, NULL)->ptr;
else
cmd = Imgdisplay;
Imgdisplay_pid = open_pipe_rw(&Imgdisplay_rf, &Imgdisplay_wf);
if (Imgdisplay_pid < 0)
goto err0;
if (Imgdisplay_pid == 0) {
/* child */
char *cmd;
setup_child(FALSE, 2, -1);
if (!strchr(Imgdisplay, '/'))
cmd = Strnew_m_charp(w3m_auxbin_dir(), "/", Imgdisplay, NULL)->ptr;
else
cmd = Imgdisplay;
myExec(cmd);
/* XXX: ifdef __EMX__, use start /f ? */
}
@@ -333,6 +334,9 @@ loadImage(Buffer *buf, int flag)
struct stat st;
int i, draw = FALSE;
/* int wait_st; */
#ifdef DONT_CALL_GC_AFTER_FORK
char *loadargs[7];
#endif
if (maxLoadImage > MAX_LOAD_IMAGE)
maxLoadImage = MAX_LOAD_IMAGE;
@@ -433,6 +437,24 @@ loadImage(Buffer *buf, int flag)
image_cache[i] = cache;
flush_tty();
#ifdef DONT_CALL_GC_AFTER_FORK
loadargs[0] = MyProgramName;
loadargs[1] = "-$$getimage";
loadargs[2] = conv_to_system(cache->url);
loadargs[3] = conv_to_system(parsedURL2Str(cache->current)->ptr);
loadargs[4] = cache->file;
loadargs[5] = cache->touch;
loadargs[6] = NULL;
if ((cache->pid = fork()) == 0) {
setup_child(FALSE, 0, -1);
execvp(MyProgramName, loadargs);
exit(1);
}
else if (cache->pid < 0) {
cache->pid = 0;
return;
}
#else /* !DONT_CALL_GC_AFTER_FORK */
if ((cache->pid = fork()) == 0) {
Buffer *b;
/*
@@ -458,6 +480,7 @@ loadImage(Buffer *buf, int flag)
cache->pid = 0;
return;
}
#endif /* !DONT_CALL_GC_AFTER_FORK */
}
}
+105
View File
@@ -721,6 +721,111 @@ shell_quote(char *str)
return str;
}
void *
xrealloc(void *ptr, size_t size)
{
void *newptr = realloc(ptr, size);
if (newptr == NULL) {
fprintf(stderr, "Out of memory\n");
exit(-1);
}
return newptr;
}
/* Define this as a separate function in case the free() has
* an incompatible prototype. */
void
xfree(void *ptr)
{
free(ptr);
}
void *
w3m_GC_realloc_atomic(void *ptr, size_t size)
{
return ptr ? GC_REALLOC(ptr, size) : GC_MALLOC_ATOMIC(size);
}
void
w3m_GC_free(void *ptr)
{
GC_FREE(ptr);
}
void
growbuf_init(struct growbuf *gb)
{
gb->ptr = NULL;
gb->length = 0;
gb->area_size = 0;
gb->realloc_proc = &w3m_GC_realloc_atomic;
gb->free_proc = &w3m_GC_free;
}
void
growbuf_init_without_GC(struct growbuf *gb)
{
gb->ptr = NULL;
gb->length = 0;
gb->area_size = 0;
gb->realloc_proc = &xrealloc;
gb->free_proc = &xfree;
}
void
growbuf_clear(struct growbuf *gb)
{
(*gb->free_proc) (gb->ptr);
gb->ptr = NULL;
gb->length = 0;
gb->area_size = 0;
}
Str
growbuf_to_Str(struct growbuf *gb)
{
Str s;
if (gb->free_proc == &w3m_GC_free) {
growbuf_reserve(gb, gb->length + 1);
gb->ptr[gb->length] = '\0';
s = New(struct _Str);
s->ptr = gb->ptr;
s->length = gb->length;
s->area_size = gb->area_size;
} else {
s = Strnew_charp_n(gb->ptr, gb->length);
(*gb->free_proc) (gb->ptr);
}
gb->ptr = NULL;
gb->length = 0;
gb->area_size = 0;
return s;
}
void
growbuf_reserve(struct growbuf *gb, int leastarea)
{
int newarea;
if (gb->area_size < leastarea) {
newarea = gb->area_size * 3 / 2;
if (newarea < leastarea)
newarea = leastarea;
newarea += 16;
gb->ptr = (*gb->realloc_proc) (gb->ptr, newarea);
gb->area_size = newarea;
}
}
void
growbuf_append(struct growbuf *gb, const char *src, int len)
{
growbuf_reserve(gb, gb->length + len);
memcpy(&gb->ptr[gb->length], src, len);
gb->length += len;
}
static char *
w3m_dir(const char *name, char *dft)
{
+23
View File
@@ -12,6 +12,14 @@
#define FALSE 0
#endif /* FALSE */
struct growbuf {
char *ptr;
int length;
int area_size;
void *(*realloc_proc) (void *, size_t);
void (*free_proc) (void *);
};
#define RAW_MODE 0
#define PAGER_MODE 1
#define HTML_MODE 2
@@ -65,6 +73,18 @@ extern Str Str_url_unquote(Str x, int is_form, int safe);
extern Str Str_form_quote(Str x);
#define Str_form_unquote(x) Str_url_unquote((x), TRUE, FALSE)
extern char *shell_quote(char *str);
#define xmalloc(s) xrealloc(NULL, s)
extern void *xrealloc(void *ptr, size_t size);
extern void xfree(void *ptr);
extern void *w3m_GC_realloc_atomic(void *ptr, size_t size);
extern void w3m_GC_free(void *ptr);
extern void growbuf_init(struct growbuf *gb);
extern void growbuf_init_without_GC(struct growbuf *gb);
extern void growbuf_clear(struct growbuf *gb);
extern Str growbuf_to_Str(struct growbuf *gb);
extern void growbuf_reserve(struct growbuf *gb, int leastarea);
extern void growbuf_append(struct growbuf *gb, const char *src, int len);
#define GROWBUF_ADD_CHAR(gb,ch) ((((gb)->length>=(gb)->area_size)?growbuf_reserve(gb,(gb)->length+1):(void)0),(void)((gb)->ptr[(gb)->length++] = (ch)))
extern char *w3m_auxbin_dir();
extern char *w3m_lib_dir();
@@ -77,5 +97,8 @@ extern char *w3m_help_dir();
#define New_N(type,n) ((type*)GC_MALLOC((n)*sizeof(type)))
#define NewAtom_N(type,n) ((type*)GC_MALLOC_ATOMIC((n)*sizeof(type)))
#define New_Reuse(type,ptr,n) ((type*)GC_REALLOC((ptr),(n)*sizeof(type)))
#define NewWithoutGC(type) ((type*)xmalloc(sizeof(type)))
#define NewWithoutGC_N(type,n) ((type*)xmalloc((n)*sizeof(type)))
#define NewWithoutGC_Reuse(type,ptr,n) ((type*)xrealloc(ptr,(n)*sizeof(type)))
#endif /* INDEP_H */
+123 -119
View File
@@ -35,12 +35,14 @@ static int ssl_read(struct ssl_handle *handle, char *buf, int len);
static int ens_read(struct ens_handle *handle, char *buf, int len);
static void ens_close(struct ens_handle *handle);
static void memchop(char *p, int *len);
static void
do_update(BaseStream base)
{
int len;
base->stream.cur = base->stream.next = 0;
len = base->read(base->handle, base->stream.buf, base->stream.size);
len = (*base->read) (base->handle, base->stream.buf, base->stream.size);
if (len <= 0)
base->iseos = TRUE;
else
@@ -66,12 +68,12 @@ init_buffer(BaseStream base, char *buf, int bufsize)
StreamBuffer sb = &base->stream;
sb->size = bufsize;
sb->cur = 0;
sb->buf = NewWithoutGC_N(uchar, bufsize);
if (buf) {
sb->buf = (uchar *) buf;
memcpy(sb->buf, buf, bufsize);
sb->next = bufsize;
}
else {
sb->buf = NewAtom_N(uchar, bufsize);
sb->next = 0;
}
base->iseos = FALSE;
@@ -95,10 +97,10 @@ newInputStream(int des)
InputStream stream;
if (des < 0)
return NULL;
stream = New(union input_stream);
stream = NewWithoutGC(union input_stream);
init_base_stream(&stream->base, STREAM_BUF_SIZE);
stream->base.type = IST_BASIC;
stream->base.handle = New(int);
stream->base.handle = NewWithoutGC(int);
*(int *)stream->base.handle = des;
stream->base.read = (int (*)())basic_read;
stream->base.close = (void (*)())basic_close;
@@ -111,10 +113,10 @@ newFileStream(FILE * f, void (*closep) ())
InputStream stream;
if (f == NULL)
return NULL;
stream = New(union input_stream);
stream = NewWithoutGC(union input_stream);
init_base_stream(&stream->base, STREAM_BUF_SIZE);
stream->file.type = IST_FILE;
stream->file.handle = New(struct io_file_handle);
stream->file.handle = NewWithoutGC(struct io_file_handle);
stream->file.handle->f = f;
if (closep)
stream->file.handle->close = closep;
@@ -131,10 +133,10 @@ newStrStream(Str s)
InputStream stream;
if (s == NULL)
return NULL;
stream = New(union input_stream);
stream = NewWithoutGC(union input_stream);
init_str_stream(&stream->base, s);
stream->str.type = IST_STR;
stream->str.handle = s;
stream->str.handle = NULL;
stream->str.read = (int (*)())str_read;
stream->str.close = NULL;
return stream;
@@ -147,10 +149,10 @@ newSSLStream(SSL * ssl, int sock)
InputStream stream;
if (sock < 0)
return NULL;
stream = New(union input_stream);
stream = NewWithoutGC(union input_stream);
init_base_stream(&stream->base, SSL_BUF_SIZE);
stream->ssl.type = IST_SSL;
stream->ssl.handle = New(struct ssl_handle);
stream->ssl.handle = NewWithoutGC(struct ssl_handle);
stream->ssl.handle->ssl = ssl;
stream->ssl.handle->sock = sock;
stream->ssl.read = (int (*)())ssl_read;
@@ -166,14 +168,14 @@ newEncodedStream(InputStream is, char encoding)
if (is == NULL || (encoding != ENC_QUOTE && encoding != ENC_BASE64 &&
encoding != ENC_UUENCODE))
return is;
stream = New(union input_stream);
stream = NewWithoutGC(union input_stream);
init_base_stream(&stream->base, STREAM_BUF_SIZE);
stream->ens.type = IST_ENCODED;
stream->ens.handle = New(struct ens_handle);
stream->ens.handle = NewWithoutGC(struct ens_handle);
stream->ens.handle->is = is;
stream->ens.handle->pos = 0;
stream->ens.handle->encoding = encoding;
stream->ens.handle->s = NULL;
growbuf_init_without_GC(&stream->ens.handle->gb);
stream->ens.read = (int (*)())ens_read;
stream->ens.close = (void (*)())ens_close;
return stream;
@@ -187,8 +189,10 @@ ISclose(InputStream stream)
stream->base.type & IST_UNCLOSE)
return -1;
prevtrap = mySignal(SIGINT, SIG_IGN);
stream->base.close(stream->base.handle);
stream->base.close (stream->base.handle);
mySignal(SIGINT, prevtrap);
xfree(stream->base.stream.buf);
xfree(stream);
return 0;
}
@@ -218,122 +222,97 @@ ISundogetc(InputStream stream)
return -1;
}
#define MARGIN_STR_SIZE 10
Str
StrISgets(InputStream stream)
StrISgets2(InputStream stream, char crnl)
{
BaseStream base;
StreamBuffer sb;
Str s = NULL;
uchar *p;
int len;
struct growbuf gb;
if (stream == NULL)
return '\0';
base = &stream->base;
sb = &base->stream;
return NULL;
growbuf_init(&gb);
ISgets_to_growbuf(stream, &gb, crnl);
return growbuf_to_Str(&gb);
}
void
ISgets_to_growbuf(InputStream stream, struct growbuf *gb, char crnl)
{
BaseStream base = &stream->base;
StreamBuffer sb = &base->stream;
int i;
gb->length = 0;
while (!base->iseos) {
if (MUST_BE_UPDATED(base)) {
do_update(base);
continue;
}
else {
if ((p = memchr(&sb->buf[sb->cur], '\n', sb->next - sb->cur))) {
len = p - &sb->buf[sb->cur] + 1;
if (s == NULL)
s = Strnew_size(len);
Strcat_charp_n(s, (char *)&sb->buf[sb->cur], len);
sb->cur += len;
return s;
if (crnl && gb->length > 0 && gb->ptr[gb->length - 1] == '\r') {
if (sb->buf[sb->cur] == '\n') {
GROWBUF_ADD_CHAR(gb, '\n');
++sb->cur;
}
else {
if (s == NULL)
s = Strnew_size(sb->next - sb->cur + MARGIN_STR_SIZE);
Strcat_charp_n(s, (char *)&sb->buf[sb->cur],
sb->next - sb->cur);
sb->cur = sb->next;
break;
}
for (i = sb->cur; i < sb->next; ++i) {
if (sb->buf[i] == '\n' || (crnl && sb->buf[i] == '\r')) {
++i;
break;
}
}
growbuf_append(gb, &sb->buf[sb->cur], i - sb->cur);
sb->cur = i;
if (gb->length > 0 && gb->ptr[gb->length - 1] == '\n')
break;
}
if (s == NULL)
return Strnew();
return s;
}
Str
StrmyISgets(InputStream stream)
{
BaseStream base;
StreamBuffer sb;
Str s = NULL;
int i, len;
if (stream == NULL)
return '\0';
base = &stream->base;
sb = &base->stream;
while (!base->iseos) {
if (MUST_BE_UPDATED(base)) {
do_update(base);
}
else {
if (s && Strlastchar(s) == '\r') {
if (sb->buf[sb->cur] == '\n')
Strcat_char(s, (char)sb->buf[sb->cur++]);
return s;
}
for (i = sb->cur;
i < sb->next && sb->buf[i] != '\n' && sb->buf[i] != '\r';
i++) ;
if (i < sb->next) {
len = i - sb->cur + 1;
if (s == NULL)
s = Strnew_size(len + MARGIN_STR_SIZE);
Strcat_charp_n(s, (char *)&sb->buf[sb->cur], len);
sb->cur = i + 1;
if (sb->buf[i] == '\n')
return s;
}
else {
if (s == NULL)
s = Strnew_size(sb->next - sb->cur + MARGIN_STR_SIZE);
Strcat_charp_n(s, (char *)&sb->buf[sb->cur],
sb->next - sb->cur);
sb->cur = sb->next;
}
}
}
if (s == NULL)
return Strnew();
return s;
growbuf_reserve(gb, gb->length + 1);
gb->ptr[gb->length] = '\0';
return;
}
#ifdef unused
int
ISread(InputStream stream, Str buf, int count)
{
int rest, len;
int len;
if (count + 1 > buf->area_size) {
char *newptr = GC_MALLOC_ATOMIC(count + 1);
memcpy(newptr, buf->ptr, buf->length);
newptr[buf->length] = '\0';
buf->ptr = newptr;
buf->area_size = count + 1;
}
len = ISread_n(stream, buf->ptr, count);
buf->length = (len > 0) ? len : 0;
buf->ptr[buf->length] = '\0';
return (len > 0) ? 1 : 0;
}
#endif
int
ISread_n(InputStream stream, char *dst, int count)
{
int len, l;
BaseStream base;
if (stream == NULL || (base = &stream->base)->iseos)
if (stream == NULL || count <= 0)
return -1;
if ((base = &stream->base)->iseos)
return 0;
len = buffer_read(&base->stream, buf->ptr, count);
rest = count - len;
len = buffer_read(&base->stream, dst, count);
if (MUST_BE_UPDATED(base)) {
len = base->read(base->handle, &buf->ptr[len], rest);
if (len <= 0) {
l = (*base->read) (base->handle, &dst[len], count - len);
if (l <= 0) {
base->iseos = TRUE;
len = 0;
} else {
len += l;
}
rest -= len;
}
Strtruncate(buf, count - rest);
if (buf->length > 0)
return 1;
return 0;
return len;
}
int
@@ -645,6 +624,7 @@ basic_close(int *handle)
#else
close(*(int *)handle);
#endif
xfree(handle);
}
static int
@@ -661,6 +641,7 @@ static void
file_close(struct io_file_handle *handle)
{
handle->close(handle->f);
xfree(handle);
}
static int
@@ -682,6 +663,7 @@ ssl_close(struct ssl_handle *handle)
close(handle->sock);
if (handle->ssl)
SSL_free(handle->ssl);
xfree(handle);
}
static int
@@ -717,38 +699,60 @@ static void
ens_close(struct ens_handle *handle)
{
ISclose(handle->is);
growbuf_clear(&handle->gb);
xfree(handle);
}
static int
ens_read(struct ens_handle *handle, char *buf, int len)
{
if (handle->s == NULL || handle->pos == handle->s->length) {
if (handle->pos == handle->gb.length) {
char *p;
handle->s = StrmyISgets(handle->is);
if (handle->s->length == 0)
struct growbuf gbtmp;
ISgets_to_growbuf(handle->is, &handle->gb, TRUE);
if (handle->gb.length == 0)
return 0;
cleanup_line(handle->s, PAGER_MODE);
if (handle->encoding == ENC_BASE64)
Strchop(handle->s);
memchop(handle->gb.ptr, &handle->gb.length);
else if (handle->encoding == ENC_UUENCODE) {
if (!strncmp(handle->s->ptr, "begin", 5))
handle->s = StrmyISgets(handle->is);
Strchop(handle->s);
if (handle->gb.length >= 5 &&
!strncmp(handle->gb.ptr, "begin", 5))
ISgets_to_growbuf(handle->is, &handle->gb, TRUE);
memchop(handle->gb.ptr, &handle->gb.length);
}
p = handle->s->ptr;
growbuf_init_without_GC(&gbtmp);
p = handle->gb.ptr;
if (handle->encoding == ENC_QUOTE)
handle->s = decodeQP(&p);
decodeQP_to_growbuf(&gbtmp, &p);
else if (handle->encoding == ENC_BASE64)
handle->s = decodeB(&p);
decodeB_to_growbuf(&gbtmp, &p);
else if (handle->encoding == ENC_UUENCODE)
handle->s = decodeU(&p);
decodeU_to_growbuf(&gbtmp, &p);
growbuf_clear(&handle->gb);
handle->gb = gbtmp;
handle->pos = 0;
}
if (len > handle->s->length - handle->pos)
len = handle->s->length - handle->pos;
if (len > handle->gb.length - handle->pos)
len = handle->gb.length - handle->pos;
bcopy(&handle->s->ptr[handle->pos], buf, len);
memcpy(buf, &handle->gb.ptr[handle->pos], len);
handle->pos += len;
return len;
}
static void
memchop(char *p, int *len)
{
char *q;
for (q = p + *len; q > p; --q) {
if (q[-1] != '\n' && q[-1] != '\r')
break;
}
if (q != p + *len)
*q = '\0';
*len = q - p;
return;
}
+9 -4
View File
@@ -2,13 +2,13 @@
#ifndef IO_STREAM_H
#define IO_STREAM_H
#include "indep.h"
#include <stdio.h>
#ifdef USE_SSL
#include <openssl/bio.h>
#include <openssl/x509.h>
#include <openssl/ssl.h>
#endif
#include "Str.h"
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
@@ -36,7 +36,7 @@ union input_stream;
struct ens_handle {
union input_stream *is;
Str s;
struct growbuf gb;
int pos;
char encoding;
};
@@ -119,9 +119,14 @@ extern InputStream newEncodedStream(InputStream is, char encoding);
extern int ISclose(InputStream stream);
extern int ISgetc(InputStream stream);
extern int ISundogetc(InputStream stream);
extern Str StrISgets(InputStream stream);
extern Str StrmyISgets(InputStream stream);
extern Str StrISgets2(InputStream stream, char crnl);
#define StrISgets(stream) StrISgets2(stream, FALSE)
#define StrmyISgets(stream) StrISgets2(stream, TRUE)
void ISgets_to_growbuf(InputStream stream, struct growbuf *gb, char crnl);
#ifdef unused
extern int ISread(InputStream stream, Str buf, int count);
#endif
int ISread_n(InputStream stream, char *dst, int bufsize);
extern int ISfileno(InputStream stream);
extern int ISeos(InputStream stream);
#ifdef USE_SSL
+14 -5
View File
@@ -359,6 +359,10 @@ localcgi_post(char *uri, char *qstr, FormList *request, char *referer)
int status;
pid_t pid;
char *file = uri, *name = uri, *path_info = NULL, *tmpf = NULL;
#ifdef HAVE_CHDIR
char *cgi_dir;
#endif
char *cgi_basename;
#ifdef __MINGW32_VERSION
return NULL;
@@ -373,7 +377,14 @@ localcgi_post(char *uri, char *qstr, FormList *request, char *referer)
if (!fw)
return NULL;
}
if (qstr)
uri = Strnew_m_charp(uri, "?", qstr, NULL)->ptr;
#ifdef HAVE_CHDIR
cgi_dir = mydirname(file);
#endif
cgi_basename = mybasename(file);
pid = open_pipe_rw(&fr, NULL);
/* Don't invoke gc after here, or the program might crash in some platforms */
if (pid < 0)
return NULL;
else if (pid) {
@@ -383,8 +394,6 @@ localcgi_post(char *uri, char *qstr, FormList *request, char *referer)
}
setup_child(TRUE, 2, fw ? fileno(fw) : -1);
if (qstr)
uri = Strnew_m_charp(uri, "?", qstr, NULL)->ptr;
set_cgi_environ(name, file, uri);
if (path_info)
set_environ("PATH_INFO", path_info);
@@ -415,11 +424,11 @@ localcgi_post(char *uri, char *qstr, FormList *request, char *referer)
}
#ifdef HAVE_CHDIR /* ifndef __EMX__ ? */
chdir(mydirname(file));
chdir(cgi_dir);
#endif
execl(file, mybasename(file), NULL);
execl(file, cgi_basename, NULL);
fprintf(stderr, "execl(\"%s\", \"%s\", NULL): %s\n",
file, mybasename(file), strerror(errno));
file, cgi_basename, strerror(errno));
exit(1);
return NULL;
#endif
+44
View File
@@ -11,6 +11,9 @@
#include <sys/wait.h>
#endif
#include <time.h>
#if defined(__CYGWIN__) && defined(USE_BINMODE_STREAM)
#include <io.h>
#endif
#include "terms.h"
#include "myctype.h"
#include "regex.h"
@@ -407,6 +410,10 @@ main(int argc, char **argv, char **envp)
wc_ces CodePage;
#endif
#endif
#if defined(DONT_CALL_GC_AFTER_FORK) && defined(USE_IMAGE)
char **getimage_args = NULL;
#endif /* defined(DONT_CALL_GC_AFTER_FORK) && defined(USE_IMAGE) */
GC_INIT();
#if defined(ENABLE_NLS) || (defined(USE_M17N) && defined(HAVE_LANGINFO_CODESET))
setlocale(LC_ALL, "");
@@ -428,6 +435,10 @@ main(int argc, char **argv, char **envp)
CurrentDir = currentdir();
CurrentPid = (int)getpid();
#if defined(DONT_CALL_GC_AFTER_FORK) && defined(USE_IMAGE)
if (argv[0] && *argv[0])
MyProgramName = argv[0];
#endif /* defined(DONT_CALL_GC_AFTER_FORK) && defined(USE_IMAGE) */
BookmarkFile = NULL;
config_file = NULL;
@@ -751,6 +762,15 @@ main(int argc, char **argv, char **envp)
else if (!strcmp("-reqlog",argv[i])) {
w3m_reqlog=rcFile("request.log");
}
#if defined(DONT_CALL_GC_AFTER_FORK) && defined(USE_IMAGE)
else if (!strcmp("-$$getimage", argv[i])) {
++i;
getimage_args = argv + i;
i += 4;
if (i > argc)
usage();
}
#endif /* defined(DONT_CALL_GC_AFTER_FORK) && defined(USE_IMAGE) */
else {
usage();
}
@@ -839,6 +859,30 @@ main(int argc, char **argv, char **envp)
if (w3m_backend)
backend();
#if defined(DONT_CALL_GC_AFTER_FORK) && defined(USE_IMAGE)
if (getimage_args) {
char *image_url = conv_from_system(getimage_args[0]);
char *base_url = conv_from_system(getimage_args[1]);
ParsedURL base_pu;
parseURL2(base_url, &base_pu, NULL);
image_source = getimage_args[2];
newbuf = loadGeneralFile(image_url, &base_pu, NULL, 0, NULL);
if (!newbuf || !newbuf->real_type ||
strncasecmp(newbuf->real_type, "image/", 6))
unlink(getimage_args[2]);
#if defined(HAVE_SYMLINK) && defined(HAVE_LSTAT)
symlink(getimage_args[2], getimage_args[3]);
#else
{
FILE *f = fopen(getimage_args[3], "w");
if (f)
fclose(f);
}
#endif
w3m_exit(0);
}
#endif /* defined(DONT_CALL_GC_AFTER_FORK) && defined(USE_IMAGE) */
if (w3m_dump)
mySignal(SIGINT, SIG_IGN);
+48 -15
View File
@@ -63,13 +63,23 @@ ha2d(char x, char y)
Str
decodeB(char **ww)
{
struct growbuf gb;
growbuf_init(&gb);
decodeB_to_growbuf(&gb, ww);
return growbuf_to_Str(&gb);
}
void
decodeB_to_growbuf(struct growbuf *gb, char **ww)
{
unsigned char c[4];
char *wp = *ww;
char d[3];
int i, n_pad;
Str ap = Strnew_size(strlen(wp));
growbuf_reserve(gb, strlen(wp) + 1);
n_pad = 0;
while (1) {
for (i = 0; i < 4; i++) {
@@ -93,39 +103,50 @@ decodeB(char **ww)
for (i = 0; i < 4; i++) {
c[i] = c2e(c[i]);
if (c[i] == BAD_BASE64) {
*ww = wp;
return ap;
goto last;
}
}
d[0] = ((c[0] << 2) | (c[1] >> 4));
d[1] = ((c[1] << 4) | (c[2] >> 2));
d[2] = ((c[2] << 6) | c[3]);
for (i = 0; i < 3 - n_pad; i++) {
Strcat_char(ap, d[i]);
GROWBUF_ADD_CHAR(gb, d[i]);
}
if (n_pad || *wp == '\0' || *wp == '?')
break;
}
last:
growbuf_reserve(gb, gb->length + 1);
gb->ptr[gb->length] = '\0';
*ww = wp;
return ap;
return;
}
Str
decodeU(char **ww)
{
struct growbuf gb;
growbuf_init(&gb);
decodeU_to_growbuf(&gb, ww);
return growbuf_to_Str(&gb);
}
void
decodeU_to_growbuf(struct growbuf *gb, char **ww)
{
unsigned char c1, c2;
char *w = *ww;
int n, i;
Str a;
if (*w <= 0x20 || *w >= 0x60)
return Strnew_size(0);
return;
n = *w - 0x20;
a = Strnew_size(n);
growbuf_reserve(gb, n + 1);
for (w++, i = 2; *w != '\0' && n; n--) {
c1 = (w[0] - 0x20) % 0x40;
c2 = (w[1] - 0x20) % 0x40;
Strcat_char(a, (c1 << i) | (c2 >> (6 - i)));
gb->ptr[gb->length++] = (c1 << i) | (c2 >> (6 - i));
if (i == 6) {
w += 2;
i = 2;
@@ -135,7 +156,8 @@ decodeU(char **ww)
i += 2;
}
}
return a;
gb->ptr[gb->length] = '\0';
return;
}
/* RFC2047 (4.2. The "Q" encoding) */
@@ -165,9 +187,19 @@ decodeQ(char **ww)
Str
decodeQP(char **ww)
{
char *w = *ww;
Str a = Strnew_size(strlen(w));
struct growbuf gb;
growbuf_init(&gb);
decodeQP_to_growbuf(&gb, ww);
return growbuf_to_Str(&gb);
}
void
decodeQP_to_growbuf(struct growbuf *gb, char **ww)
{
char *w = *ww;
growbuf_reserve(gb, strlen(w) + 1);
for (; *w != '\0'; w++) {
if (*w == '=') {
w++;
@@ -180,15 +212,16 @@ decodeQP(char **ww)
else {
if (*w == '\0' || *(w + 1) == '\0')
break;
Strcat_char(a, ha2d(*w, *(w + 1)));
gb->ptr[gb->length++] = ha2d(*w, *(w + 1));
w++;
}
}
else
Strcat_char(a, *w);
gb->ptr[gb->length++] = *w;
}
gb->ptr[gb->length] = '\0';
*ww = w;
return a;
return;
}
#ifdef USE_M17N
+3 -2
View File
@@ -607,9 +607,12 @@ extern char *getAnchorText(Buffer *buf, AnchorList *al, Anchor *a);
extern Buffer *link_list_panel(Buffer *buf);
extern Str decodeB(char **ww);
extern void decodeB_to_growbuf(struct growbuf *gb, char **ww);
extern Str decodeQ(char **ww);
extern Str decodeQP(char **ww);
extern void decodeQP_to_growbuf(struct growbuf *gb, char **ww);
extern Str decodeU(char **ww);
extern void decodeU_to_growbuf(struct growbuf *gb, char **ww);
#ifdef USE_M17N
extern Str decodeWord(char **ow, wc_ces * charset);
extern Str decodeMIME(Str orgstr, wc_ces * charset);
@@ -811,5 +814,3 @@ extern void dispVer(void);
void srand48(long);
long lrand48(void);
#endif
#include "indep.h"