diff options
author | FreeArtMan <dos21h@gmail.com> | 2014-12-09 10:31:37 +0900 |
---|---|---|
committer | FreeArtMan <dos21h@gmail.com> | 2014-12-09 10:31:37 +0900 |
commit | a57c6bed8f6ab7d0f4355190c0cff7cd913da6a0 (patch) | |
tree | c8b85b9de364cb63678d05625bdff6a2cf12ecda | |
parent | dc4bbe5366d6c733f9f77b7c9fee0cbba3e0d92b (diff) | |
download | microbbs-a57c6bed8f6ab7d0f4355190c0cff7cd913da6a0.tar.gz microbbs-a57c6bed8f6ab7d0f4355190c0cff7cd913da6a0.zip |
New planned functionality. Menuconfig support. Simple captcha.
-rw-r--r-- | Kconfig | 60 | ||||
-rw-r--r-- | Makefile | 10 | ||||
-rw-r--r-- | articles.c | 7 | ||||
-rw-r--r-- | articles.h | 2 | ||||
-rw-r--r-- | bbsconfig.c | 1 | ||||
-rw-r--r-- | bbsconfig.h | 7 | ||||
-rw-r--r-- | buildinfo.h | 2 | ||||
-rw-r--r-- | captcha.c | 16 | ||||
-rw-r--r-- | captcha.h | 18 | ||||
-rw-r--r-- | file_use.c | 198 | ||||
-rw-r--r-- | file_use.h | 40 | ||||
-rw-r--r-- | ini.c | 181 | ||||
-rw-r--r-- | ini.h | 77 | ||||
-rw-r--r-- | inih/LICENSE.txt | 27 | ||||
-rw-r--r-- | inih/README.txt | 5 | ||||
-rw-r--r-- | kconf2h/kconf2h.c | 50 | ||||
-rw-r--r-- | kconf2h/kconf2h.h | 10 | ||||
-rw-r--r-- | kconf2h/kconf2h_parser.c | 327 | ||||
-rw-r--r-- | kconfig.h | 7 | ||||
-rw-r--r-- | list.c | 180 | ||||
-rw-r--r-- | list.h | 83 | ||||
-rw-r--r-- | login.c | 3 | ||||
-rw-r--r-- | login.h | 6 | ||||
-rw-r--r-- | microbbs.c | 108 | ||||
-rw-r--r-- | motd.c | 6 | ||||
-rw-r--r-- | motd.h | 2 | ||||
-rw-r--r-- | session.c | 1 | ||||
-rw-r--r-- | session.h | 4 | ||||
-rw-r--r-- | statistics.c | 1 | ||||
-rw-r--r-- | statistics.h | 4 | ||||
-rw-r--r-- | telnetd.c | 0 | ||||
-rw-r--r-- | telnetd.h | 0 | ||||
-rw-r--r-- | textview.c | 0 | ||||
-rw-r--r-- | textview.h | 0 |
34 files changed, 1428 insertions, 15 deletions
@@ -0,0 +1,60 @@ +menuconfig TODO + bool "List of todo" + option todo + +if TODO +endif + +menuconfig TWIT + bool "Twit soem short messages" + option twit + default n + +if TWIT +endif + +menuconfig DOORGAMES + bool "Door games" + option doorgames + default n + +if DOORGAMES +endif + +menuconfig BOARD + bool "Messaging board" + option board + default n + +if BOARD +endif + +menuconfig LOGIN + bool "User login support" + option login + default n + +if LOGIN +endif + +menuconfig ARTICLES + bool "Read articles" + option articles + default y + +if ARTICLES +endif + +menuconfig MOTD + bool "Motd message" + option motd + default y + +if MOTD +endif + + + +config CAPTCHA + bool "Enable simple captcha" + default y @@ -1,7 +1,7 @@ PROJECT=microbbs CC=gcc CFLAGS= -SOURCES=motd.c buildinfo.c sysinfo.c articles.c logs.c vote.c list.c mmm.c +SOURCES=articles.c bbsconfig.c buildinfo.c captcha.c file_use.c ini.c list.c login.c logs.c mmm.c motd.c session.c statistics.c sysinfo.c telnetd.c textview.c vote.c OBJECTS=$(SOURCES:.c=.o) BUILD_DIR=build_dir @@ -10,6 +10,14 @@ all: mkdir $(OBJECTS) $(PROJECT) mkdir: mkdir -p $(BUILD_DIR) +kconfig2h: + $(CC) -c kconf2h/kconf2h_parser.c + $(CC) kconf2h/kconf2h.c kconf2h_parser.o -o kconf2h/kconf2h + +menuconfig: kconfig2h + ./mconf Kconfig + kconf2h/kconf2h .config kconfig.h + $(PROJECT): $(SOURCES) cd ./libterm; make $(CC) $(addprefix $(BUILD_DIR)/,$(OBJECTS)) $(CFLAGS) libterm/libterm.o microbbs.c -o $(PROJECT) @@ -1,5 +1,7 @@ #include "articles.h" +#ifdef CONFIG_ARTICLES + //TODO add checkout on size of art it will fix, // warn about cutted images int bbs_article( term_screen *ts, const char *fname ) @@ -26,7 +28,7 @@ int bbs_article( term_screen *ts, const char *fname ) max_y = 24; } - bbs_log_article( NULL ); + bbs_log_article( fname ); if ( fname != NULL ) { @@ -161,7 +163,6 @@ int bbs_article_list( term_screen *ts, const char *dir_name ) if ( path_node.st_mode & S_IFREG ) { llist_push( dir_list, cnct_path ); - printf("-->%s\n", cnct_path); } } } @@ -236,3 +237,5 @@ int bbs_article_list( term_screen *ts, const char *dir_name ) return ret; } + +#endif @@ -10,6 +10,8 @@ #include <unistd.h> #include <fcntl.h> +#include "kconfig.h" + //part of libterm #include "libterm/term.h" #include "logs.h" diff --git a/bbsconfig.c b/bbsconfig.c new file mode 100644 index 0000000..53267b8 --- /dev/null +++ b/bbsconfig.c @@ -0,0 +1 @@ +#include "bbsconfig.h"
\ No newline at end of file diff --git a/bbsconfig.h b/bbsconfig.h new file mode 100644 index 0000000..c1eb80f --- /dev/null +++ b/bbsconfig.h @@ -0,0 +1,7 @@ +#ifndef __MICROBBS_BBSCONFIG_H +#define __MICROBBS_BBSCONFIG_H + +#include <stdio.h> +#include <stdlib.h> + +#endif
\ No newline at end of file diff --git a/buildinfo.h b/buildinfo.h index 3b5964d..2d91704 100644 --- a/buildinfo.h +++ b/buildinfo.h @@ -4,7 +4,7 @@ #include <stdio.h> #include <stdlib.h> -#define BUILD_VERSION "0.1.9" +#define BUILD_VERSION "0.2.0" #define BUILD_DATE (__DATE__) void print_build_info(); diff --git a/captcha.c b/captcha.c new file mode 100644 index 0000000..ad614be --- /dev/null +++ b/captcha.c @@ -0,0 +1,16 @@ +#include "captcha.h" + +#ifdef CONFIG_CAPTCHA + +int captcha_test1() +{ + int ret = 0; + char s[2]; + printf("Are you bot?(y/n):\n"); + fgets(s,2,stdin); + if ( s[0] == 'n' || s[0] == 'N') + ret = 1; + return ret; +} + +#endif
\ No newline at end of file diff --git a/captcha.h b/captcha.h new file mode 100644 index 0000000..d294955 --- /dev/null +++ b/captcha.h @@ -0,0 +1,18 @@ +#ifndef __MICROBBS_CAPTCHA_H +#define __MICROBBS_CAPTCHA_H + +#include <stdio.h> +#include <stdlib.h> + +#include "kconfig.h" + +//ask question if you are bot or no. In 99% cases should protect from random +//bots. +// Return: +// 0 - test not passed +// 1 - test passed +int captcha_test1(); + + + +#endif
\ No newline at end of file diff --git a/file_use.c b/file_use.c new file mode 100644 index 0000000..cd816bc --- /dev/null +++ b/file_use.c @@ -0,0 +1,198 @@ +#include "file_use.h" + + +void f_file_null( f_file *f_f ) +{ + if ( f_f ) + { + f_f->fid = NULL; + f_f->flags = 0; + f_f->size = -1; + f_f->seek = -1; + } +} + +int f_file_seek( f_file *f_f, long offset, int seek ) +{ + int ret=-1; + PRINT("\n"); + if ( f_f ) + { + if ( offset < 0 ) + { + ERROR("\n"); + return -1; + } + + if ( offset > f_f->size ) + { + ERROR("\n"); + return -1; + } + + + ret = fseek( f_f->fid, offset , seek ); + PRINT("ret=%d\n",ret); + if ( ret == 0 ) + { + f_f->seek = ret; + } + else + { + ERROR("cannot seek to %d\n", offset); + return -1; + } + PRINT("ret=%d\n",ret); + } + return ret; +} + + +size_t f_file_read( f_file *f_f, size_t size, void *ptr ) +{ + size_t ret=-1; + PRINT("\n"); + if ( f_f ) + { + if ( (f_f->flags == F_FILE_READ) || + (f_f->flags == F_FILE_RW)) + { + if ( f_f->size >= f_f->seek + f_f->size ) + { + ret = fread( ptr, 1, size, f_f->fid ); + /* + if ( ret != size ) + { + ERROR("%d != %d\n", ret, size ); + return -1; + } + else + */ + if ( ret < 0 ) + { + ERROR("\n"); + return ret; + } + } else + { + ERROR("\n"); + } + } else + { + ERROR("file writable only"); + } + } + return ret; +} + + +int f_file_size( f_file *f_f ) +{ + int ret=-1; + long old_seek; + + PRINT("\n"); + if ( f_f ) + { + //could make some logic break + if ( f_f->size < 0 ) + { + old_seek = ftell( f_f->fid ); + fseek( f_f->fid, 0, SEEK_END ); + ret = ftell( f_f->fid ); + fseek( f_f->fid, old_seek, SEEK_CUR ); + } + } + return ret; +} + + +//f_file_read_bl(); + + +size_t f_file_write( f_file *f_f, size_t size, void *ptr ) +{ + PRINT("%s\n"); + if ( f_f ) + { + if ((f_f->flags == F_FILE_WRITE) || + (f_f->flags == F_FILE_RW) ) + { + ERROR("Not yet ready\n"); + } + } + +} + + +//f_file_write_bl(); + + +f_file* f_file_open( const char *fname, int flags ) +{ + f_file *ret = NULL; + + const char *f_flags_write="r"; + const char *f_flags_read="w"; + const char *f_flags_rw="r+"; + char *f_flags_tmp=NULL; + + if ( fname != NULL ) + { + ret = malloc( sizeof( f_file ) ); + if ( ret == NULL ) + { + ERROR("Cannot alloc mem\n"); + return NULL; + } + memset( ret, 0, sizeof( f_file )); + f_file_null( ret ); + switch ( flags ) + { + case F_FILE_READ: + f_flags_tmp = f_flags_read; + ret->flags = F_FILE_READ; + break; + + case F_FILE_WRITE: + f_flags_tmp = f_flags_write; + ret->flags = F_FILE_WRITE; + break; + + case F_FILE_RW: + f_flags_tmp = f_flags_rw; + ret->flags = F_FILE_RW; + break; + + default: + ERROR("Unknown flag for opening \n"); + goto exit_close_f; + } + ret->fid = fopen( fname, "r" ); + if ( ret->fid == NULL ) + { + ERROR("Cannot open file\n"); + goto exit_close_f; + } + ret->size = f_file_size( ret ); + } + return ret; + +exit_close_f: + if ( ret != NULL ) + free( ret ); + return NULL; +} + + +int f_file_close( f_file *f_f ) +{ + PRINT("\n"); + if ( f_f ) + { + fclose( f_f->fid ); + free( f_f ); + f_f = NULL; + } +} + diff --git a/file_use.h b/file_use.h new file mode 100644 index 0000000..fe7cc08 --- /dev/null +++ b/file_use.h @@ -0,0 +1,40 @@ +#ifndef __LIBUTILS_FILE_USE_H +#define __LIBUTILS_FILE_USE_H + +#include <stdio.h> +#include <stdlib.h> +#include <string.h> + +#include "debug.h" + +#define F_FILE_NONE 0 +#define F_FILE_READ 1 +#define F_FILE_WRITE 2 +#define F_FILE_RW 3 + +#define F_SEEK_CUR SEEK_CUR +#define F_SEEK_END SEEK_END +#define F_SEEK_SET SEEK_SET + +//simple file using things +typedef struct f_file +{ + FILE *fid; + int flags; + long size; + int seek; +} f_file; + +void f_file_null( f_file* ); +int f_file_seek( f_file*, long, int ); +size_t f_file_read( f_file*, size_t, void* ); +//f_file_read_bl(); +int f_file_size( f_file* ); +size_t f_file_write( f_file*, size_t, void* ); +//f_file_write_bl(); +f_file* f_file_open( const char*, int ); +int f_file_close( f_file* ); +//f_file_flush(); +//f_file_mmap(); + +#endif @@ -0,0 +1,181 @@ +/* inih -- simple .INI file parser + +inih is released under the New BSD license (see LICENSE.txt). Go to the project +home page for more info: + +http://code.google.com/p/inih/ + +*/ + +#include <stdio.h> +#include <ctype.h> +#include <string.h> + +#include "ini.h" + +#if !INI_USE_STACK +#include <stdlib.h> +#endif + +#define MAX_SECTION 50 +#define MAX_NAME 50 + +/* Strip whitespace chars off end of given string, in place. Return s. */ +static char* rstrip(char* s) +{ + char* p = s + strlen(s); + while (p > s && isspace((unsigned char)(*--p))) + *p = '\0'; + return s; +} + +/* Return pointer to first non-whitespace char in given string. */ +static char* lskip(const char* s) +{ + while (*s && isspace((unsigned char)(*s))) + s++; + return (char*)s; +} + +/* Return pointer to first char c or ';' comment in given string, or pointer to + null at end of string if neither found. ';' must be prefixed by a whitespace + character to register as a comment. */ +static char* find_char_or_comment(const char* s, char c) +{ + int was_whitespace = 0; + while (*s && *s != c && !(was_whitespace && *s == ';')) { + was_whitespace = isspace((unsigned char)(*s)); + s++; + } + return (char*)s; +} + +/* Version of strncpy that ensures dest (size bytes) is null-terminated. */ +static char* strncpy0(char* dest, const char* src, size_t size) +{ + strncpy(dest, src, size); + dest[size - 1] = '\0'; + return dest; +} + +/* See documentation in header file. */ +int ini_parse_file(FILE* file, + int (*handler)(void*, const char*, const char*, + const char*), + void* user) +{ + /* Uses a fair bit of stack (use heap instead if you need to) */ +#if INI_USE_STACK + char line[INI_MAX_LINE]; +#else + char* line; +#endif + char section[MAX_SECTION] = ""; + char prev_name[MAX_NAME] = ""; + + char* start; + char* end; + char* name; + char* value; + int lineno = 0; + int error = 0; + +#if !INI_USE_STACK + line = (char*)malloc(INI_MAX_LINE); + if (!line) { + return -2; + } +#endif + + /* Scan through file line by line */ + while (fgets(line, INI_MAX_LINE, file) != NULL) { + lineno++; + + start = line; +#if INI_ALLOW_BOM + if (lineno == 1 && (unsigned char)start[0] == 0xEF && + (unsigned char)start[1] == 0xBB && + (unsigned char)start[2] == 0xBF) { + start += 3; + } +#endif + start = lskip(rstrip(start)); + + if (*start == ';' || *start == '#') { + /* Per Python ConfigParser, allow '#' comments at start of line */ + } +#if INI_ALLOW_MULTILINE + else if (*prev_name && *start && start > line) { + /* Non-black line with leading whitespace, treat as continuation + of previous name's value (as per Python ConfigParser). */ + if (!handler(user, section, prev_name, start) && !error) + error = lineno; + } +#endif + else if (*start == '[') { + /* A "[section]" line */ + end = find_char_or_comment(start + 1, ']'); + if (*end == ']') { + *end = '\0'; + strncpy0(section, start + 1, sizeof(section)); + *prev_name = '\0'; + } + else if (!error) { + /* No ']' found on section line */ + error = lineno; + } + } + else if (*start && *start != ';') { + /* Not a comment, must be a name[=:]value pair */ + end = find_char_or_comment(start, '='); + if (*end != '=') { + end = find_char_or_comment(start, ':'); + } + if (*end == '=' || *end == ':') { + *end = '\0'; + name = rstrip(start); + value = lskip(end + 1); + end = find_char_or_comment(value, '\0'); + if (*end == ';') + *end = '\0'; + rstrip(value); + + /* Valid name[=:]value pair found, call handler */ + strncpy0(prev_name, name, sizeof(prev_name)); + if (!handler(user, section, name, value) && !error) + error = lineno; + } + else if (!error) { + /* No '=' or ':' found on name[=:]value line */ + error = lineno; + } + } + +#if INI_STOP_ON_FIRST_ERROR + if (error) + break; +#endif + } + +#if !INI_USE_STACK + free(line); +#endif + + return error; +} + +/* See documentation in header file. */ +int ini_parse(const char* filename, + int (*handler)(void*, const char*, const char*, const char*), + void* user) +{ + FILE* file; + int error; + + file = fopen(filename, "r"); + if (!file) + return -1; + error = ini_parse_file(file, handler, user); + fclose(file); + return error; +} @@ -0,0 +1,77 @@ +/* inih -- simple .INI file parser + +inih is released under the New BSD license (see LICENSE.txt). Go to the project +home page for more info: + +http://code.google.com/p/inih/ + +*/ + +#ifndef __INI_H__ +#define __INI_H__ + +/* Make this header file easier to include in C++ code */ +#ifdef __cplusplus +extern "C" { +#endif + +#include <stdio.h> + +/* Parse given INI-style file. May have [section]s, name=value pairs + (whitespace stripped), and comments starting with ';' (semicolon). Section + is "" if name=value pair parsed before any section heading. name:value + pairs are also supported as a concession to Python's ConfigParser. + + For each name=value pair parsed, call handler function with given user + pointer as well as section, name, and value (data only valid for duration + of handler call). Handler should return nonzero on success, zero on error. + + Returns 0 on success, line number of first error on parse error (doesn't + stop on first error), -1 on file open error, or -2 on memory allocation + error (only when INI_USE_STACK is zero). +*/ +int ini_parse(const char* filename, + int (*handler)(void* user, const char* section, + const char* name, const char* value), + void* user); + +/* Same as ini_parse(), but takes a FILE* instead of filename. This doesn't + close the file when it's finished -- the caller must do that. */ +int ini_parse_file(FILE* file, + int (*handler)(void* user, const char* section, + const char* name, const char* value), + void* user); + +/* Nonzero to allow multi-line value parsing, in the style of Python's + ConfigParser. If allowed, ini_parse() will call the handler with the same + name for each subsequent line parsed. */ +#ifndef INI_ALLOW_MULTILINE +#define INI_ALLOW_MULTILINE 1 +#endif + +/* Nonzero to allow a UTF-8 BOM sequence (0xEF 0xBB 0xBF) at the start of + the file. See http://code.google.com/p/inih/issues/detail?id=21 */ +#ifndef INI_ALLOW_BOM +#define INI_ALLOW_BOM 1 +#endif + +/* Nonzero to use stack, zero to use heap (malloc/free). */ +#ifndef INI_USE_STACK +#define INI_USE_STACK 1 +#endif + +/* Stop parsing on first error (default is to keep parsing). */ +#ifndef INI_STOP_ON_FIRST_ERROR +#define INI_STOP_ON_FIRST_ERROR 0 +#endif + +/* Maximum line length for any line in INI file. */ +#ifndef INI_MAX_LINE +#define INI_MAX_LINE 200 +#endif + +#ifdef __cplusplus +} +#endif + +#endif /* __INI_H__ */ diff --git a/inih/LICENSE.txt b/inih/LICENSE.txt new file mode 100644 index 0000000..1d31de2 --- /dev/null +++ b/inih/LICENSE.txt @@ -0,0 +1,27 @@ + +The "inih" library is distributed under the New BSD license: + +Copyright (c) 2009, Brush Technology +All rights reserved. + +Redistribution and use in source and binary forms, with or without +modification, are permitted provided that the following conditions are met: + * Redistributions of source code must retain the above copyright + notice, this list of conditions and the following disclaimer. + * Redistributions in binary form must reproduce the above copyright + notice, this list of conditions and the following disclaimer in the + documentation and/or other materials provided with the distribution. + * Neither the name of Brush Technology nor the names of its contributors + may be used to endorse or promote products derived from this software + without specific prior written permission. + +THIS SOFTWARE IS PROVIDED BY BRUSH TECHNOLOGY ''AS IS'' AND ANY +EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED +WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE +DISCLAIMED. IN NO EVENT SHALL BRUSH TECHNOLOGY BE LIABLE FOR ANY +DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES +(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; +LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND +ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS +SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. diff --git a/inih/README.txt b/inih/README.txt new file mode 100644 index 0000000..8e5f8b1 --- /dev/null +++ b/inih/README.txt @@ -0,0 +1,5 @@ + +inih is a simple .INI file parser written in C, released under the New BSD +license (see LICENSE.txt). Go to the project home page for more info: + +http://code.google.com/p/inih/ diff --git a/kconf2h/kconf2h.c b/kconf2h/kconf2h.c new file mode 100644 index 0000000..91ef6c7 --- /dev/null +++ b/kconf2h/kconf2h.c @@ -0,0 +1,50 @@ +#include <stdio.h> +#include <stdlib.h> + +#include <sys/stat.h> + +#include "kconf2h.h" + +int main( int argc, char **argv ) +{ + FILE *fin = NULL; + FILE *fout = NULL; + struct stat st; + + char *buf=NULL; + if ( argc == 3 ) + { + fin = fopen( argv[1], "r+" ); + fout = fopen( argv[2], "w+" ); + fseek( fin, 0, SEEK_SET ); + if ( fin && fout ) + { + if ( stat( argv[1], &st ) ) + { + goto error_exit; + } + buf = malloc( st.st_size ); memset( buf, 0, st.st_size ); + size_t r_size = fread( buf, 1, st.st_size, fin ); + if ( r_size > 0 ) + { + int ret = parse_kconf2h( buf, fout ); + printf("Kconfig file parsed %d %d bytes\n", ret, r_size ); + } else + { + printf("ERR: while reading file %s [%d]\n", argv[1], r_size); + } +error_exit: + if ( buf ) free( buf ); + fclose( fin ); + fclose( fout ); + } else + { + printf("ERR: Cannot open file\n"); + } + } else + { + printf("ERR: usage ./kconf2h [conffile] [outputheader]\n"); + return -1; + } + return 0; +} diff --git a/kconf2h/kconf2h.h b/kconf2h/kconf2h.h new file mode 100644 index 0000000..165d4cc --- /dev/null +++ b/kconf2h/kconf2h.h @@ -0,0 +1,10 @@ +#ifndef __KCONF2H_H +#define __KCONF2H_H + +#include <stdio.h> +#include <stdlib.h> +#include <string.h> + +int parse_kconf2h( const char*, FILE* ); + +#endif diff --git a/kconf2h/kconf2h_parser.c b/kconf2h/kconf2h_parser.c new file mode 100644 index 0000000..5269c14 --- /dev/null +++ b/kconf2h/kconf2h_parser.c @@ -0,0 +1,327 @@ + +#line 1 "kconf2h_parser.ragel" +#include <stdio.h> +#include <stdlib.h> +#include <stdint.h> +#include <string.h> + +#include "kconf2h.h" + +#define TYPE_YM 1 +#define TYPE_HEX 2 +#define TYPE_STR 3 +#define TYPE_DEC 4 + +char *new_string( const char *start, const char *end ) +{ + int str_s = end-start+1; + char *new_str=malloc( str_s+1 ); + memcpy( new_str, start, str_s ); + if ( new_str != NULL ) + new_str[str_s]=0x0; + return new_str; +} + +int o_head_def( FILE *f, int type, const char *s_define, const char *e_define, + const char *s_value, const char *e_value ) +{ + if ( f != NULL ) + { + if ( (s_define != NULL) && (e_define != NULL) && (s_define <= e_define) && + (s_value != NULL) && ( e_value != NULL ) && ( s_value <= e_value )) + { + char *def = new_string( s_define, e_define ); + char *val = NULL; + //printf( "%s\n", def ); + fprintf( f, "#define %s", def ); + free( def ); + + if ( type != TYPE_YM ) + { + val = new_string( s_value, e_value ); + fprintf( f, " %s", val ); + free( val ); + } + /* + switch ( type ) + { + case TYPE_HEX: + fprintf( f, " %s", val ); + break; + case TYPE_STR: + fprintf( f, " %s", val ); + break; + case TYPE_DEC: + fprintf( f, " %s", val ); + break; + default: + printf("Unknown Kconfig type %d\n", type); + } + */ + + fprintf( f, "\n" ); + return 1; + } + } + return 0; +} + + +#line 71 "kconf2h_parser.c" +static const char _k2h_actions[] = { + 0, 1, 0, 1, 2, 1, 7, 1, + 11, 2, 9, 1, 4, 3, 8, 10, + 11, 4, 4, 8, 10, 11, 4, 5, + 8, 10, 11, 4, 6, 8, 10, 11 + +}; + +static const char _k2h_key_offsets[] = { + 0, 0, 3, 6, 7, 8, 9, 10, + 11, 12, 17, 23, 30, 33, 37, 39, + 42, 46, 52, 59, 60 +}; + +static const char _k2h_trans_keys[] = { + 10, 35, 67, 10, 32, 126, 79, 78, + 70, 73, 71, 95, 95, 48, 57, 65, + 90, 61, 95, 48, 57, 65, 90, 34, + 45, 48, 109, 121, 49, 57, 34, 32, + 126, 10, 34, 32, 126, 48, 57, 10, + 48, 57, 10, 120, 48, 57, 48, 57, + 65, 70, 97, 102, 10, 48, 57, 65, + 70, 97, 102, 10, 10, 35, 67, 0 +}; + +static const char _k2h_single_lengths[] = { + 0, 3, 1, 1, 1, 1, 1, 1, + 1, 1, 2, 5, 1, 2, 0, 1, + 2, 0, 1, 1, 3 +}; + +static const char _k2h_range_lengths[] = { + 0, 0, 1, 0, 0, 0, 0, 0, + 0, 2, 2, 1, 1, 1, 1, 1, + 1, 3, 3, 0, 0 +}; + +static const char _k2h_index_offsets[] = { + 0, 0, 4, 7, 9, 11, 13, 15, + 17, 19, 23, 28, 35, 38, 42, 44, + 47, 51, 55, 60, 62 +}; + +static const char _k2h_indicies[] = { + 0, 2, 3, 1, 0, 4, 1, 5, + 1, 6, 1, 7, 1, 8, 1, 9, + 1, 10, 1, 11, 11, 11, 1, 12, + 11, 11, 11, 1, 13, 14, 15, 17, + 17, 16, 1, 19, 18, 1, 20, 19, + 18, 1, 21, 1, 22, 21, 1, 22, + 23, 21, 1, 24, 24, 24, 1, 25, + 24, 24, 24, 1, 26, 1, 0, 2, + 3, 1, 0 +}; + +static const char _k2h_trans_targs[] = { + 20, 0, 2, 3, 2, 4, 5, 6, + 7, 8, 9, 10, 11, 12, 14, 16, + 15, 19, 12, 13, 20, 15, 20, 17, + 18, 20, 20 +}; + +static const char _k2h_trans_actions[] = { + 7, 0, 1, 9, 0, 0, 0, 0, + 0, 0, 0, 0, 3, 5, 5, 5, + 5, 5, 0, 0, 22, 0, 17, 0, + 0, 27, 12 +}; + +static const int k2h_start = 1; +static const int k2h_first_final = 20; +static const int k2h_error = 0; + +static const int k2h_en_main = 1; + + +#line 87 "kconf2h_parser.ragel" + + +int parse_kconf2h( const char *str, FILE *outf ) +{ + + + + static uint8_t cs; + const int stacksize = 10; + int res=0, *top=0, *stack=NULL; + stack = malloc( sizeof(stack)*stacksize ); + char *p=(char *)str, *pe = (char *)str + strlen( str ), *eof=NULL; + + /* + variables used in state machine + */ + char *token_s=NULL, *token_e=NULL; + char *value_s=NULL, *value_e=NULL; + int token_type=0; + fprintf( outf, "#ifndef __KCONFIG_H\n" ); + fprintf( outf, "#define __KCONFIG_H\n" ); + + +#line 172 "kconf2h_parser.c" + { + cs = k2h_start; + } + +#line 110 "kconf2h_parser.ragel" + +#line 179 "kconf2h_parser.c" + { + int _klen; + unsigned int _trans; + const char *_acts; + unsigned int _nacts; + const char *_keys; + + if ( p == pe ) + goto _test_eof; + if ( cs == 0 ) + goto _out; +_resume: + _keys = _k2h_trans_keys + _k2h_key_offsets[cs]; + _trans = _k2h_index_offsets[cs]; + + _klen = _k2h_single_lengths[cs]; + if ( _klen > 0 ) { + const char *_lower = _keys; + const char *_mid; + const char *_upper = _keys + _klen - 1; + while (1) { + if ( _upper < _lower ) + break; + + _mid = _lower + ((_upper-_lower) >> 1); + if ( (*p) < *_mid ) + _upper = _mid - 1; + else if ( (*p) > *_mid ) + _lower = _mid + 1; + else { + _trans += (unsigned int)(_mid - _keys); + goto _match; + } + } + _keys += _klen; + _trans += _klen; + } + + _klen = _k2h_range_lengths[cs]; + if ( _klen > 0 ) { + const char *_lower = _keys; + const char *_mid; + const char *_upper = _keys + (_klen<<1) - 2; + while (1) { + if ( _upper < _lower ) + break; + + _mid = _lower + (((_upper-_lower) >> 1) & ~1); + if ( (*p) < _mid[0] ) + _upper = _mid - 2; + else if ( (*p) > _mid[1] ) + _lower = _mid + 2; + else { + _trans += (unsigned int)((_mid - _keys)>>1); + goto _match; + } + } + _trans += _klen; + } + +_match: + _trans = _k2h_indicies[_trans]; + cs = _k2h_trans_targs[_trans]; + + if ( _k2h_trans_actions[_trans] == 0 ) + goto _again; + + _acts = _k2h_actions + _k2h_trans_actions[_trans]; + _nacts = (unsigned int) *_acts++; + while ( _nacts-- > 0 ) + { + switch ( *_acts++ ) + { + case 0: +#line 72 "kconf2h_parser.ragel" + {} + break; + case 1: +#line 73 "kconf2h_parser.ragel" + {token_s = p;} + break; + case 2: +#line 73 "kconf2h_parser.ragel" + {token_e = p-1;} + break; + case 3: +#line 76 "kconf2h_parser.ragel" + {token_type=TYPE_YM;} + break; + case 4: +#line 77 "kconf2h_parser.ragel" + {token_type=TYPE_DEC;} + break; + case 5: +#line 78 "kconf2h_parser.ragel" + {token_type=TYPE_STR;} + break; + case 6: +#line 79 "kconf2h_parser.ragel" + {token_type=TYPE_HEX;} + break; + case 7: +#line 79 "kconf2h_parser.ragel" + {value_s = p;} + break; + case 8: +#line 79 "kconf2h_parser.ragel" + {value_e = p-1;} + break; + case 9: +#line 80 "kconf2h_parser.ragel" + {} + break; + case 10: +#line 80 "kconf2h_parser.ragel" + { o_head_def( outf, token_type, token_s, token_e, value_s, value_e ); } + break; + case 11: +#line 82 "kconf2h_parser.ragel" + {} + break; +#line 301 "kconf2h_parser.c" + } + } + +_again: + if ( cs == 0 ) + goto _out; + if ( ++p != pe ) + goto _resume; + _test_eof: {} + _out: {} + } + +#line 111 "kconf2h_parser.ragel" + + if ( cs == k2h_error ) + { + printf("ERR state [%d] pos[%d]:[%s]\n", res, p-str, p); + res = -1; + } + + fprintf( outf, "#endif\n" ); + + return res; +} + + + diff --git a/kconfig.h b/kconfig.h new file mode 100644 index 0000000..bb80b88 --- /dev/null +++ b/kconfig.h @@ -0,0 +1,7 @@ +#ifndef __KCONFIG_H +#define __KCONFIG_H +#define CONFIG_TODO +#define CONFIG_ARTICLES +#define CONFIG_MOTD +#define CONFIG_CAPTCHA +#endif @@ -39,8 +39,9 @@ int llist_index( struct List *list, void *ptr ) } -void llist_reverse( struct List **list ) +void llist_reverse( struct List *list ) { + ERROR("\n"); //abort(0); } @@ -108,6 +109,67 @@ void llist_push( struct List *list, void *ptr ) } +void* llist_removen( struct List *l, struct ListNode *ln ) +{ + ListNode *ret=NULL; + ListNode *iter = l->first; + ListNode *prev_iter = NULL; + + if ( iter == NULL ) + goto result_ready; + + while ( iter->next != NULL ) + { + if ( iter == ln ) + { + break; + } + prev_iter = iter; + iter = iter->next; + } + ret = iter; + iter = NULL; //dont use iter anymore pls + + if ( ret != NULL ) + { + //if first element of list + //the prev=NULL + if ( prev_iter == NULL ) + { + //if only one element in da list? + + if ( l->first == l->last ) + { + l->first = NULL; + l->last = NULL; + } else + //if more then one element + { + l->first = l->first->next; + } + ret->next = NULL; + goto result_ready; + } + + //if last element of the list + if ( ret == l->last ) + { + prev_iter->next = NULL; + l->last = prev_iter; + goto result_ready; + } + + //if in da middle + prev_iter->next = ((ListNode *)ret)->next; + ((ListNode *)ret)->next = NULL; + + + } + +result_ready: + return ret; +} + void llist_free( struct List *list ) { @@ -137,6 +199,122 @@ void llist_free( struct List *list ) void llist_freen( struct ListNode *node ) { + ERROR("\n"); +} + + + +void llist_sortn( struct List *list, clb_llist_cmp clb_cmp) +{ + int print_list( List *ln ) + { + if ( ln == NULL ) return; + char *ptr=NULL; + ListNode *l = ln->first; + + while ( l != NULL ) + { + ptr = l->val; + printf("%s", ptr); + if ( l->next != NULL ) + { + printf("(->%s) ",(char*)l->next->val ); + } + //printf("\n"); + l = l->next; + } + printf("\n"); + + return 1; + } + + int print_node( ListNode *n ) + { + if ( n == NULL ) return; + while ( n != NULL ) + { + printf("%s ", (char*)n->val); + n = n->next; + } + printf("\n"); + } + + + //creat new empty list and add all elements sorted + struct ListNode *sorted=NULL, *last=NULL, *get=NULL; + + get = llist_removen( list, list->first ); + sorted = get; + get = llist_removen( list, list->first ); + + while ( get != NULL ) + { + //add to empty in sorted like place + struct ListNode *iter = sorted; + struct ListNode *prev_iter = malloc( sizeof(struct ListNode)); + memset( prev_iter, 0, sizeof(struct ListNode)); + prev_iter->next = iter; + while ( iter != NULL ) + { + //there could be that no empty element in da list + if ( get == NULL ) break; + if ( clb_cmp( iter->val, get->val ) >= 0 ) + { + //add to sorted list end if everything is ok + if ( iter->next == NULL ) + { + iter->next = get; + break; + } + } else + { + prev_iter->next = get; + prev_iter = get; + get->next = iter; + if ( iter == sorted ) + { + sorted = prev_iter; + } + iter = prev_iter; + + break; + } + prev_iter = iter; + iter = iter->next; + } + get = llist_removen( list, list->first ); + } + list->first = sorted; +} + +int llist_save( struct List *l, clb_llist_save clb_save ) +{ + int ret=0, frc=0; + if ( l == NULL ) return ret; + if ( clb_save == NULL ) return ret; + + /* + struct ListNode *iter = llist_first( l ); + + while ( iter != NULL ) + { + clb_save( ); + iter = iter->next; + } + */ + frc = clb_save( "/tmp/binlist.txt", l ); + if ( frc != 0) + ret = -1; + return ret; } +struct List* llist_load( clb_llist_load clb_load, const char *fname ) +{ + int ret = 0; + struct List *loaded = NULL; + + ret = clb_load( (char *)fname, (void **)loaded ); + + return loaded; +} @@ -10,42 +10,102 @@ //use stack memallocation features. need to make some changes in api +//!TODO give for_each macros that can be used +//!TODO add insert element in list for sorting stuff +//!TODO save/load could be just void* list->val that to save, sequently + + +//when need to compare 2 nodes values with are pointers on anything +// return: +// -1 (<) void 1 is less then void 2 +// 0 (=) void 1 is equal to void 2 +// 1 (>) void 1 is bigger then void 2 +typedef int (*clb_llist_cmp)(void *, void *); + +//when need to free whole list and also values of list with are just pointer +//to anything +// param void* - list->val +typedef int (*clb_llist_free)(void *); + +//load and save data to file if possible +//return +// 0 - everything is ok +// non-zero - something went wrong +// can put different errors that you whant +//param +//void* - string where to save, or how to save +//void* - linked list that need to save +typedef int (*clb_llist_save)(void *, void *); +//return +// non-zero - some error happened +// 0 - everything is ok +//param +//void* - string from where to load +//void* - list where to save +typedef int (*clb_llist_load)(void *, void **); typedef struct ListNode { struct ListNode *next; - void *val; + void *val; } ListNode; typedef struct List { - int count; + int count; ListNode *first; ListNode *last; } List; +typedef struct ListManager +{ + List *list; + int sorted; //auto sort if needed + int mode; // read only + char *name; // list name + clb_llist_cmp *cmp; + clb_llist_free *free; + clb_llist_save *save; + clb_llist_load *load; +} ListManager; + + + + struct List* llist_new(); struct ListNode* llist_newn( void* ); +struct ListManager* llist_newm(); //#define __LLIST_NEW() //#define __LLIST_NEWN() int llist_length( struct List* ); int llist_index( struct List*, void* ); //llist_find( struct List ); -//find by pointer -//find by value -void llist_reverse( struct List** ); +//!find by pointer +//!find by value + +void llist_reverse( struct List* ); + +//void llist_append( struct List*, void* ); -void llist_append( struct List*, void* ); void llist_appendn( struct List**, void*, struct ListNode* ); //#define __LIST_APPEND() +// get one element from list and erease it from list void* llist_pop( struct List* ); +//add at the end one element void llist_push( struct List*, void* ); +//remove node from list and return value of element +//void* llist_remove( struct List*, struct ListNode* ); +void* llist_removen( struct List*, struct ListNode* ); +//delete one element from the list +//void llist_delete( struct List*, void*); + void llist_free( struct List* ); void llist_freen( struct ListNode* ); + //void llist_merge( struct List**, struct List* ); //void llist_compare( struct List //void llist_split( struct List*, @@ -53,8 +113,12 @@ void llist_freen( struct ListNode* ); //void llist_splitp( struct List*, void* //void llist_splitc( struct List*, void (*)(void*) //void llist_sort( -//sort by pointer -//sort by value +//!sort by pointer +//!sort by val value, need compare callback +void llist_sortn( struct List*, clb_llist_cmp ); + +int llist_save( struct List*, clb_llist_save ); +struct List* llist_load( clb_llist_load, const char* ); #define llist_first(A) ((A)->first) #define llist_last(A) ((A)->last) @@ -66,4 +130,7 @@ void llist_freen( struct ListNode* ); //#define llist_isfirstn(A) () //#define llist_getfirstn(A) ((A)) //#define llist_getlastn(A) () + + + #endif @@ -0,0 +1,3 @@ +#include "login.h" + + @@ -0,0 +1,6 @@ +#ifndef __MICROBBS_LOGIN_H +#define __MICROBBS_LOGIN_H + + + +#endif
\ No newline at end of file @@ -1,6 +1,7 @@ #include <stdio.h> #include <stdlib.h> +#include "kconfig.h" #include "logs.h" #include "motd.h" #include "libterm/term.h" @@ -16,36 +17,139 @@ int main( int argc, char **argv ) term_init_data( &ts ); //printf("%d %d\n", ts.term_col, ts.term_row); + //lunch captcha and try to detect if its random bot +#ifdef CONFIG_CAPTCHA + if ( captcha_test1() != 1) + return 1; +#endif + //write to log that some user have accesed bbs + //too much fake stuff comes to log //bbs_log( NULL ); //write to default place +#ifdef CONFIG_MOTD bbs_login_motd( &ts, "art/motd.txt" ); print_build_info(); +#endif + while ( strncmp( str, "q", 1 ) && strncmp( str, "Q", 1 ) ) { - printf("(M)otd (Q)uit (S)ysinfo (A)rticles: "); + #ifdef CONFIG_MOTD + printf("(M)otd "); + #endif + + #ifdef CONFIG_ARTICLES + printf("(A)rticles "); + #endif + + #ifdef CONFIG_DOORGAMES + printf("(D)oor games "); + #endif + + #ifdef CONFIG_TWIT + printf("(T)wit "); + #endif + + #ifdef CONFIG_BOARD + printf("(B)oard "); + #endif + + #ifdef CONFIG_LOGIN + printf("(L)ogin "); + #endif + + #ifdef CONFIG_TODO + printf("T(o)do "); + #endif + printf("(Q)uit (S)ysinfo Mesa(G)es: "); ret_len = getline( &str, &str_size, stdin ); if ( ret_len > 0) { switch ( str[0] ) { + //------------------------------------------------------------------ + #ifdef CONFIG_MOTD case 'm': case 'M': { bbs_login_motd( &ts, "art/motd.txt" ); } break; + #endif case 's': case 'S': { bbs_sysinfo( &ts ); } break; + + //------------------------------------------------------------------ + #ifdef CONFIG_ARTICLES case 'a': case 'A': { bbs_article_list( &ts, "./article/" ); } break; + #endif + + //------------------------------------------------------------------ + #ifdef CONFIG_TWIT + case 't': + case 'T': + { + printf("Twitter like\n"); + } + break; + #endif + + //------------------------------------------------------------------ + #ifdef CONFIG_DOORGAMES + case 'd': + case 'D': + { + printf("Door games\n"); + } + break; + #endif + + case 'g': + case 'G': + { + printf("Messages\n"); + } + break; + + //------------------------------------------------------------------ + #ifdef CONFIG_BOARD + case 'b': + case 'B': + { + printf("Board\n"); + } + break; + #endif + + + //------------------------------------------------------------------ + #ifdef CONFIG_LOGIN + case 'l': + case 'L': + { + printf("Login?\n"); + } + break; + #endif + + //------------------------------------------------------------------ + #ifdef CONFIG_TODO + case 'o': + case 'O': + { + printf("Todo list\n"); + } + break; + #endif + case 'q': case 'Q': bbs_log_quit( NULL ); @@ -55,6 +159,8 @@ int main( int argc, char **argv ) } } } +#ifdef CONFIG_MOTD bbs_quit_motd( &ts, "art/quit.txt" ); +#endif return 0; } @@ -1,5 +1,7 @@ #include "motd.h" +#ifdef CONFIG_MOTD + //TODO merge 2 functions in one proper //TODO complcations with libterm int bbs_login_motd( term_screen *ts, const char *fname ) @@ -100,4 +102,6 @@ int bbs_quit_motd( term_screen *ts, const char *fname ) //printf("%d %d %d\n",y,posy,ts->term_row); return 0; -}
\ No newline at end of file +} + +#endif
\ No newline at end of file @@ -5,6 +5,8 @@ #include <stdlib.h> #include <string.h> +#include "kconfig.h" + #include "libterm/print_utils.h" #include "libterm/term.h" diff --git a/session.c b/session.c new file mode 100644 index 0000000..ca88985 --- /dev/null +++ b/session.c @@ -0,0 +1 @@ +#include "session.h"
\ No newline at end of file diff --git a/session.h b/session.h new file mode 100644 index 0000000..e91c679 --- /dev/null +++ b/session.h @@ -0,0 +1,4 @@ +#ifndef __MICROBBS_SESSION_H +#define __MICROBBS_SESSION_H + +#endif
\ No newline at end of file diff --git a/statistics.c b/statistics.c new file mode 100644 index 0000000..3e0ff33 --- /dev/null +++ b/statistics.c @@ -0,0 +1 @@ +#include "statistics.h"
\ No newline at end of file diff --git a/statistics.h b/statistics.h new file mode 100644 index 0000000..a91e988 --- /dev/null +++ b/statistics.h @@ -0,0 +1,4 @@ +#ifndef __MICROBBS_STATISTICS_H +#define __MICROBBS_STATISTICS_H + +#endif
\ No newline at end of file diff --git a/telnetd.c b/telnetd.c new file mode 100644 index 0000000..e69de29 --- /dev/null +++ b/telnetd.c diff --git a/telnetd.h b/telnetd.h new file mode 100644 index 0000000..e69de29 --- /dev/null +++ b/telnetd.h diff --git a/textview.c b/textview.c new file mode 100644 index 0000000..e69de29 --- /dev/null +++ b/textview.c diff --git a/textview.h b/textview.h new file mode 100644 index 0000000..e69de29 --- /dev/null +++ b/textview.h |