phpbbs.file.c
来自「linux/unix环境下的建站系统」· C语言 代码 · 共 736 行 · 第 1/2 页
C
736 行
#include "php_kbs_bbs.h" #include "SAPI.h"#include "md5.h"/* * refer Ecma-262 * '\033' -> \r (not exactly the same thing, but borrow...) * '\n' -> \n * '\\' -> \\ * '\'' -> \' * '\"' -> \" * '\0' -> possible start of attachment * 0 <= char < 32 -> ignore * others -> passthrough */PHP_FUNCTION(bbs2_readfile){ char *filename; int filename_len; char *output_buffer; int output_buffer_len, output_buffer_size, j; char c; char *ptr, *cur_ptr; off_t ptrlen, mmap_ptrlen; int in_chinese = false; int chunk_size = 51200; if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "s", &filename, &filename_len) == FAILURE) { WRONG_PARAM_COUNT; } if (safe_mmapfile(filename, O_RDONLY, PROT_READ, MAP_SHARED, &ptr, &mmap_ptrlen, NULL) == 0) RETURN_LONG(-1); j = ptrlen = mmap_ptrlen; if (j > chunk_size) j = chunk_size; output_buffer_size = 2 * j + 16; output_buffer = (char* )emalloc(output_buffer_size); output_buffer_len = 0; cur_ptr = ptr; strcpy(output_buffer + output_buffer_len, "prints('"); output_buffer_len += 8; while (1) { for (; j > 0 ; j--) { c = *cur_ptr; if (c == '\0') { //assume ATTACHMENT_PAD[0] is '\0' if (ptrlen >= ATTACHMENT_SIZE + sizeof(int) + 2) { if (!memcmp(cur_ptr, ATTACHMENT_PAD, ATTACHMENT_SIZE)) { ptrlen = -ptrlen; break; } } ptrlen--; cur_ptr++; continue; } if (c < 0) { in_chinese = !in_chinese; output_buffer[output_buffer_len++] = c; } else { do { if (c == '\n') c = 'n'; else if (c == '\033') c = 'r'; else if (c != '\\' && c != '\'' && c != '\"' && c != '/' /* to prevent things like </script> */ ) { if (c >= 32) { output_buffer[output_buffer_len++] = c; } break; } if (in_chinese && c == 'n') { output_buffer[output_buffer_len++] = ' '; } output_buffer[output_buffer_len++] = '\\'; output_buffer[output_buffer_len++] = c; } while(0); in_chinese = false; } ptrlen--; cur_ptr++; } if (ptrlen <= 0) break; j = ptrlen; if (j > chunk_size) j = chunk_size; output_buffer_size += 2 * j; output_buffer = (char*)erealloc(output_buffer, output_buffer_size); if (output_buffer == NULL) RETURN_LONG(3); } if (in_chinese) { output_buffer[output_buffer_len++] = ' '; } strcpy(output_buffer + output_buffer_len, "');"); output_buffer_len += 3; if (ptrlen < 0) { //attachment char *attachfilename, *attachptr; char buf[1024]; char *startbufptr, *bufptr; long attach_len, attach_pos, newlen; int l; ptrlen = -ptrlen; strcpy(buf, "attach('"); startbufptr = buf + strlen(buf); while(ptrlen > 0) { if (((attachfilename = checkattach(cur_ptr, ptrlen, &attach_len, &attachptr)) == NULL)) { break; } attach_pos = attachfilename - ptr; newlen = attachptr - cur_ptr + attach_len; cur_ptr += newlen; ptrlen -= newlen; if (ptrlen < 0) break; bufptr = startbufptr; while(*attachfilename != '\0') { switch(*attachfilename) { case '\'': case '\"': case '\\': *bufptr++ = '\\'; /* TODO: boundary check */ /* break is missing *intentionally* */ default: *bufptr++ = *attachfilename++; /* TODO: boundary check */ } } sprintf(bufptr, "', %ld, %ld);", attach_len, attach_pos); /* TODO: boundary check */ l = strlen(buf); if (output_buffer_len + l > output_buffer_size) { output_buffer_size = output_buffer_size + sizeof(buf) * 10; output_buffer = (char*)erealloc(output_buffer, output_buffer_size); if (output_buffer == NULL) RETURN_LONG(3); } strcpy(output_buffer + output_buffer_len, buf); output_buffer_len += l; } } end_mmapfile(ptr, mmap_ptrlen, -1); RETVAL_STRINGL(output_buffer, output_buffer_len, 0);}PHP_FUNCTION(bbs2_readfile_text){ char *filename; int filename_len; long maxchar; long escape_flag; /* 0(default) - escape <>&, 1 - double escape <>&, 2 - escape <>& and space */ char *output_buffer; int output_buffer_len, output_buffer_size, last_return = 0; char c; char *ptr, *cur_ptr; off_t ptrlen, mmap_ptrlen; int in_escape = false, is_last_space = false; int i; char escape_seq[4][16], escape_seq_len[4]; if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "sll", &filename, &filename_len, &maxchar, &escape_flag) == FAILURE) { WRONG_PARAM_COUNT; } if (safe_mmapfile(filename, O_RDONLY, PROT_READ, MAP_SHARED, &ptr, &mmap_ptrlen, NULL) == 0) RETURN_LONG(-1); ptrlen = mmap_ptrlen; if (!maxchar) { maxchar = ptrlen; } else if (ptrlen > maxchar) { ptrlen = maxchar; } output_buffer_size = 2 * maxchar; output_buffer = (char* )emalloc(output_buffer_size); output_buffer_len = 0; cur_ptr = ptr; if (escape_flag == 1) { strcpy(escape_seq[0], "&amp;"); strcpy(escape_seq[1], "&lt;"); strcpy(escape_seq[2], "&gt;"); strcpy(escape_seq[3], "<br/>"); } else { strcpy(escape_seq[0], "&"); strcpy(escape_seq[1], "<"); strcpy(escape_seq[2], ">"); strcpy(escape_seq[3], "<br/>"); } for (i=0;i<4;i++) escape_seq_len[i] = strlen(escape_seq[i]); while (ptrlen > 0) { c = *cur_ptr; if (c == '\0') { //assume ATTACHMENT_PAD[0] is '\0' break; } else if (c == '\033') { in_escape = true; } else if (!in_escape) { if (output_buffer_len + 16 > output_buffer_size) { output_buffer = (char*)erealloc(output_buffer, output_buffer_size += 128); } if (escape_flag == 2 && c == ' ') { if (!is_last_space) { output_buffer[output_buffer_len++] = ' '; } else { strcpy(output_buffer + output_buffer_len, " "); output_buffer_len += 6; } is_last_space = !is_last_space; } else { is_last_space = false; switch(c) { case '&': strcpy(output_buffer + output_buffer_len, escape_seq[0]); output_buffer_len += escape_seq_len[0]; break; case '<': strcpy(output_buffer + output_buffer_len, escape_seq[1]); output_buffer_len += escape_seq_len[1]; break; case '>': strcpy(output_buffer + output_buffer_len, escape_seq[2]); output_buffer_len += escape_seq_len[2]; break; case '\n': strcpy(output_buffer + output_buffer_len, escape_seq[3]); output_buffer_len += escape_seq_len[3]; last_return = output_buffer_len; is_last_space = true; break; default: if (c < 0 || c >= 32) output_buffer[output_buffer_len++] = c; break; } } } else if (isalpha(c)) { in_escape = false; } ptrlen--; cur_ptr++; } end_mmapfile(ptr, mmap_ptrlen, -1); RETVAL_STRINGL(output_buffer, last_return, 0);}PHP_FUNCTION(bbs_file_output_attachment){ char *filename; int filename_len; char *attachname = NULL; int attachname_len = 0; long attachpos; char *ptr; char *sendptr = NULL; int sendlen; off_t ptrlen, mmap_ptrlen; if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "sl|s", &filename, &filename_len, &attachpos, &attachname, &attachname_len) == FAILURE) { WRONG_PARAM_COUNT; } if (attachpos == 0 && attachname == NULL) { RETURN_LONG(-2); } if (safe_mmapfile(filename, O_RDONLY, PROT_READ, MAP_SHARED, &ptr, &mmap_ptrlen, NULL) == 0) RETURN_LONG(-1); ptrlen = mmap_ptrlen; if (attachpos == 0) { sendptr = ptr; sendlen = ptrlen; } else if (attachpos >= 0 && attachpos < ptrlen) { char *p, *pend = ptr + ptrlen; p = attachname = ptr + attachpos; while(*p && p < pend) { p++; } p++; if (p <= pend - 4) { memcpy(&sendlen, p, 4); sendlen = ntohl(sendlen); if (sendlen >= 0 && pend - 4 - p >= sendlen) { sendptr = p + 4; } } } if (sendptr) { sapi_header_line ctr = {0}; char buf[256]; ctr.line = buf; snprintf(buf, 256, "Content-Type: %s", get_mime_type(attachname)); ctr.line_len = strlen(buf); sapi_header_op(SAPI_HEADER_ADD, &ctr TSRMLS_CC); snprintf(buf, 256, "Accept-Ranges: bytes"); ctr.line_len = strlen(buf); sapi_header_op(SAPI_HEADER_ADD, &ctr TSRMLS_CC); snprintf(buf, 256, "Content-Length: %d", sendlen); ctr.line_len = strlen(buf); sapi_header_op(SAPI_HEADER_ADD, &ctr TSRMLS_CC); snprintf(buf, 256, "Content-Disposition: inline;filename=%s", attachname); ctr.line_len = strlen(buf); sapi_header_op(SAPI_HEADER_ADD, &ctr TSRMLS_CC); ZEND_WRITE(sendptr, sendlen); } end_mmapfile(ptr, mmap_ptrlen, -1); RETURN_LONG(0);}static char* output_buffer=NULL;static int output_buffer_len=0;static int output_buffer_size=0;void reset_output_buffer() { output_buffer=NULL; output_buffer_size=0; output_buffer_len=0;}static void output_printf(const char* buf, uint len){ int bufLen; int n,newsize; char * newbuf; if (output_buffer==NULL) { output_buffer=(char* )emalloc(51200); //first 50k if (output_buffer==NULL) { return; } output_buffer_size=51200; } bufLen=strlen(buf); if (bufLen>len) { bufLen=len; } n=1+output_buffer_len+bufLen-output_buffer_size; if (n>=0) { newsize=output_buffer_size+((n/102400)+1)*102400; //n*100k every time newbuf=(char*)erealloc(output_buffer,newsize); if (newbuf==NULL){ return; } output_buffer=newbuf; output_buffer_size=newsize; } memcpy(output_buffer+output_buffer_len,buf,bufLen); output_buffer_len+=bufLen;}static char* get_output_buffer(){ return output_buffer;}static int get_output_buffer_len(){ int len=output_buffer_len; output_buffer_len=0;
⌨️ 快捷键说明
复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?