static void _parse_left_whitespace(CSVScanner *self) { if ((self->options->flags & CSV_SCANNER_STRIP_WHITESPACE) == 0) return; _skip_whitespace(&self->src); }
/* * Skip comments */ void _lex::_skip_comment(void) { if(get_char() != COMMENT) return; while(get_char() != NEWLINE) if(!next_char()) return; _skip_whitespace(); }
/* * Enumerate new token */ void _lex::_enum_token(void) { trace( LEX_TRACE_ENABLE, TRACE_ENTRY, "lex::enum_token" ); _txt.clear(); if(has_prev_token()) { token_t tok = _cache.at(_cache_pos); if(IS_TOK_TYPE(tok.type, LEX_TOKEN_SYMBOL) && IS_SYMBOL_TYPE(tok.text, TOK_SYMBOL_QUOTE)) { _rd_mode = !_rd_mode; if(_rd_mode) { _enum_string(); return; } } } _skip_whitespace(); if(!has_next_char()) { _typ = LEX_TOKEN_END; return; } if(isalpha(get_char())) _enum_keyword(); else if(isdigit(get_char()) || get_char() == UNARY_NEG) _enum_number(); else { if(get_char() == UNDERSCORE) _enum_keyword(); else _enum_symbol(); } trace( LEX_TRACE_ENABLE, TRACE_EXIT, "lex::enum_token" ); }
static chimp_bool_t _parse_const_int (const char **ptr, ChimpRef **value) { int64_t i = 0; const char *p = *ptr; chimp_bool_t neg; _skip_whitespace (&p); neg = (*p == '-'); if (*p == '-' || *p == '+') p++; while (*p && isdigit (*p)) { i *= (int64_t) 10; i += (*p) - '0'; p++; } *value = chimp_int_new (i); *ptr = p; return *value != NULL; }
static chimp_bool_t _parse_const (const char **ptr, ChimpRef **value) { const char *p = *ptr; _skip_whitespace (&p); if (*p == '"') { if (_parse_const_str (&p, value)) { *ptr = p; return CHIMP_TRUE; } return CHIMP_FALSE; } else if (isdigit (*p)) { if (_parse_const_int (&p, value)) { *ptr = p; return CHIMP_TRUE; } return CHIMP_FALSE; } else { return CHIMP_FALSE; } }
static chimp_bool_t _parse_name (const char **ptr, ChimpRef **op) { const char *begin; const char *p = *ptr; size_t len = 0; _skip_whitespace (&p); begin = p; if (*p != '_' && !isalpha(*p)) { return CHIMP_FALSE; } while (*p && (*p == '_' || isalnum(*p))) { len++; p++; } if (len == 0) return CHIMP_FALSE; *op = chimp_str_new (begin, len); if (*op == NULL) { return CHIMP_FALSE; } *ptr = p; return CHIMP_TRUE; }
static chimp_bool_t _parse_const_str (const char **ptr, ChimpRef **value) { const char *begin; const char *p = *ptr; size_t len = 0; _skip_whitespace (&p); p++; begin = p; while (*p && *p != '"') { len++; p++; } if (!*p) { return CHIMP_FALSE; } p++; *value = chimp_str_new (begin, len); if (!*value) { return CHIMP_FALSE; } *ptr = p; return CHIMP_TRUE; }
static ChimpRef * assemble_module (const char *filename) { char buf[8192]; ChimpRef *code; ChimpRef *mod; ChimpRef *method; FILE *stream = fopen (filename, "r"); if (stream == NULL) { fprintf (stderr, "error: failed to open %s\n", filename); return NULL; } code = chimp_code_new (); if (code == NULL) { fprintf (stderr, "error: failed to allocate code object\n"); return NULL; } while (!feof (stream)) { const char *ptr; ChimpRef *opname; ChimpOpcode opcode; if (fgets (buf, sizeof(buf)-1, stream) == NULL) { break; } ptr = buf; _skip_whitespace (&ptr); if (!*ptr) continue; if (*ptr == '#') continue; if (!_parse_name (&ptr, &opname)) { fprintf (stderr, "error: expected name\n"); goto error; } opcode = _str_to_opcode (CHIMP_STR_DATA (opname)); switch (opcode) { case CHIMP_OPCODE_PUSHNIL: { if (!chimp_code_pushnil (code)) { goto error; } break; } case CHIMP_OPCODE_DUP: { if (!chimp_code_dup (code)) { goto error; } break; } case CHIMP_OPCODE_NOT: { if (!chimp_code_not (code)) { goto error; } break; } case CHIMP_OPCODE_RET: { if (!chimp_code_ret (code)) { goto error; } break; } case CHIMP_OPCODE_SPAWN: { if (!chimp_code_spawn (code)) { goto error; } break; } case CHIMP_OPCODE_MAKEARRAY: { ChimpRef *nargs; if (!_parse_const_int (&ptr, &nargs)) { goto error; } if (!chimp_code_makearray ( code, CHIMP_INT(nargs)->value)) { goto error; } break; } case CHIMP_OPCODE_MAKECLOSURE: { if (!chimp_code_makeclosure (code)) { goto error; } break; } case CHIMP_OPCODE_POP: { if (!chimp_code_pop (code)) { goto error; } break; } case CHIMP_OPCODE_PUSHNAME: { ChimpRef *name; if (!_parse_name (&ptr, &name)) { goto error; } if (!chimp_code_pushname (code, name)) { goto error; } break; } case CHIMP_OPCODE_STORENAME: { ChimpRef *name; if (!_parse_name (&ptr, &name)) { goto error; } if (!chimp_code_storename (code, name)) { goto error; } break; } case CHIMP_OPCODE_GETATTR: { ChimpRef *name; if (!_parse_name (&ptr, &name)) { goto error; } if (!chimp_code_getattr (code, name)) { goto error; } break; } case CHIMP_OPCODE_GETITEM: { if (!chimp_code_getitem (code)) { goto error; } break; } case CHIMP_OPCODE_PUSHCONST: { ChimpRef *value; if (!_parse_const (&ptr, &value)) { goto error; } if (!chimp_code_pushconst (code, value)) { goto error; } break; } case CHIMP_OPCODE_ADD: { if (!chimp_code_add (code)) { goto error; } break; } case CHIMP_OPCODE_SUB: { if (!chimp_code_sub (code)) { goto error; } break; } case CHIMP_OPCODE_MUL: { if (!chimp_code_mul (code)) { goto error; } break; } case CHIMP_OPCODE_DIV: { if (!chimp_code_div (code)) { goto error; } break; } case CHIMP_OPCODE_GETCLASS: { if (!chimp_code_getclass (code)) { goto error; } break; } case CHIMP_OPCODE_CALL: { ChimpRef *nargs; if (!_parse_const_int (&ptr, &nargs)) { goto error; } if (!chimp_code_call ( code, (uint8_t) CHIMP_INT(nargs)->value)) { goto error; } break; } default: fprintf (stderr, "error: unknown or unsupported opname: %s\n", CHIMP_STR_DATA (opname)); goto error; }; _skip_whitespace (&ptr); if (*ptr) { fprintf (stderr, "error: too many arguments for op: %s\n", CHIMP_STR_DATA(opname)); goto error; } } fclose (stream); /* printf ("%s\n", CHIMP_STR_DATA (chimp_code_dump (code))); */ mod = chimp_module_new_str ("main", NULL); if (mod == NULL) { return NULL; } method = chimp_method_new_bytecode (mod, code); if (method == NULL) { return NULL; } if (!chimp_module_add_local (mod, CHIMP_STR_NEW("main"), method)) { return NULL; } return mod; error: fclose (stream); return NULL; }