static Folder* S_init_folder(Obj *index, bool_t create) { Folder *folder = NULL; // Validate or acquire a Folder. if (Obj_Is_A(index, FOLDER)) { folder = (Folder*)INCREF(index); } else if (Obj_Is_A(index, CHARBUF)) { folder = (Folder*)FSFolder_new((CharBuf*)index); } else { THROW(ERR, "Invalid type for 'index': %o", Obj_Get_Class_Name(index)); } // Validate or create the index directory. if (create) { Folder_Initialize(folder); } else { if (!Folder_Check(folder)) { THROW(ERR, "Folder '%o' failed check", Folder_Get_Path(folder)); } } return folder; }
bool_t RAMFolder_local_delete(RAMFolder *self, const CharBuf *name) { Obj *entry = Hash_Fetch(self->entries, (Obj*)name); if (entry) { if (Obj_Is_A(entry, RAMFILE)) { ; } else if (Obj_Is_A(entry, FOLDER)) { RAMFolder *inner_folder; if (Obj_Is_A(entry, COMPOUNDFILEREADER)) { inner_folder = (RAMFolder*)CERTIFY( CFReader_Get_Real_Folder((CompoundFileReader*)entry), RAMFOLDER); } else { inner_folder = (RAMFolder*)CERTIFY(entry, RAMFOLDER); } if (Hash_Get_Size(inner_folder->entries)) { // Can't delete non-empty dir. return false; } } else { return false; } DECREF(Hash_Delete(self->entries, (Obj*)name)); return true; } else { return false; } }
void Hash_serialize(Hash *self, OutStream *outstream) { Obj *key; Obj *val; uint32_t charbuf_count = 0; OutStream_Write_C32(outstream, self->size); // Write CharBuf keys first. CharBuf keys are the common case; grouping // them together is a form of run-length-encoding and saves space, since // we omit the per-key class name. Hash_Iterate(self); while (Hash_Next(self, &key, &val)) { if (Obj_Is_A(key, CHARBUF)) { charbuf_count++; } } OutStream_Write_C32(outstream, charbuf_count); Hash_Iterate(self); while (Hash_Next(self, &key, &val)) { if (Obj_Is_A(key, CHARBUF)) { Obj_Serialize(key, outstream); FREEZE(val, outstream); } } // Punt on the classes of the remaining keys. Hash_Iterate(self); while (Hash_Next(self, &key, &val)) { if (!Obj_Is_A(key, CHARBUF)) { FREEZE(key, outstream); FREEZE(val, outstream); } } }
CharBuf* Json_to_json(Obj *dump) { // Validate object type, only allowing hashes and arrays per JSON spec. if (!dump || !(Obj_Is_A(dump, HASH) || Obj_Is_A(dump, VARRAY))) { if (!tolerant) { CharBuf *class_name = dump ? Obj_Get_Class_Name(dump) : NULL; CharBuf *mess = MAKE_MESS("Illegal top-level object type: %o", class_name); Err_set_error(Err_new(mess)); return NULL; } } // Encode. CharBuf *json = CB_new(31); if (!S_to_json(dump, json, 0)) { DECREF(json); ERR_ADD_FRAME(Err_get_error()); json = NULL; } else { // Append newline. CB_Cat_Trusted_Str(json, "\n", 1); } return json; }
void Indexer_add_index(Indexer *self, Obj *index) { Folder *other_folder = NULL; IndexReader *reader = NULL; if (Obj_Is_A(index, FOLDER)) { other_folder = (Folder*)INCREF(index); } else if (Obj_Is_A(index, CHARBUF)) { other_folder = (Folder*)FSFolder_new((CharBuf*)index); } else { THROW(ERR, "Invalid type for 'index': %o", Obj_Get_Class_Name(index)); } reader = IxReader_open((Obj*)other_folder, NULL, NULL); if (reader == NULL) { THROW(ERR, "Index doesn't seem to contain any data"); } else { Schema *schema = self->schema; Schema *other_schema = IxReader_Get_Schema(reader); VArray *other_fields = Schema_All_Fields(other_schema); VArray *seg_readers = IxReader_Seg_Readers(reader); uint32_t i, max; // Validate schema compatibility and add fields. Schema_Eat(schema, other_schema); // Add fields to Segment. for (i = 0, max = VA_Get_Size(other_fields); i < max; i++) { CharBuf *other_field = (CharBuf*)VA_Fetch(other_fields, i); Seg_Add_Field(self->segment, other_field); } DECREF(other_fields); // Add all segments. for (i = 0, max = VA_Get_Size(seg_readers); i < max; i++) { SegReader *seg_reader = (SegReader*)VA_Fetch(seg_readers, i); DeletionsReader *del_reader = (DeletionsReader*)SegReader_Fetch( seg_reader, VTable_Get_Name(DELETIONSREADER)); Matcher *deletions = del_reader ? DelReader_Iterator(del_reader) : NULL; I32Array *doc_map = DelWriter_Generate_Doc_Map(self->del_writer, deletions, SegReader_Doc_Max(seg_reader), (int32_t)Seg_Get_Count(self->segment) ); SegWriter_Add_Segment(self->seg_writer, seg_reader, doc_map); DECREF(deletions); DECREF(doc_map); } DECREF(seg_readers); } DECREF(reader); DECREF(other_folder); }
static Folder* S_derive_folder(Obj *index) { Folder *folder = NULL; if (Obj_Is_A(index, FOLDER)) { folder = (Folder*)INCREF(index); } else if (Obj_Is_A(index, CHARBUF)) { folder = (Folder*)FSFolder_new((CharBuf*)index); } else { THROW(ERR, "Invalid type for 'index': %o", Obj_Get_Class_Name(index)); } return folder; }
FullTextType* FullTextType_load(FullTextType *self, Obj *dump) { UNUSED_VAR(self); Hash *source = (Hash*)CERTIFY(dump, HASH); CharBuf *class_name = (CharBuf*)Hash_Fetch_Str(source, "_class", 6); VTable *vtable = (class_name != NULL && Obj_Is_A((Obj*)class_name, CHARBUF)) ? VTable_singleton(class_name, NULL) : FULLTEXTTYPE; FullTextType *loaded = (FullTextType*)VTable_Make_Obj(vtable); // Extract boost. Obj *boost_dump = Hash_Fetch_Str(source, "boost", 5); float boost = boost_dump ? (float)Obj_To_F64(boost_dump) : 1.0f; // Find boolean properties. Obj *indexed_dump = Hash_Fetch_Str(source, "indexed", 7); Obj *stored_dump = Hash_Fetch_Str(source, "stored", 6); Obj *sort_dump = Hash_Fetch_Str(source, "sortable", 8); Obj *hl_dump = Hash_Fetch_Str(source, "highlightable", 13); bool_t indexed = indexed_dump ? Obj_To_Bool(indexed_dump) : true; bool_t stored = stored_dump ? Obj_To_Bool(stored_dump) : true; bool_t sortable = sort_dump ? Obj_To_Bool(sort_dump) : false; bool_t hl = hl_dump ? Obj_To_Bool(hl_dump) : false; // Extract an Analyzer. Obj *analyzer_dump = Hash_Fetch_Str(source, "analyzer", 8); Analyzer *analyzer = NULL; if (analyzer_dump) { if (Obj_Is_A(analyzer_dump, ANALYZER)) { // Schema munged the dump and installed a shared analyzer. analyzer = (Analyzer*)INCREF(analyzer_dump); } else if (Obj_Is_A((Obj*)analyzer_dump, HASH)) { analyzer = (Analyzer*)Obj_Load(analyzer_dump, analyzer_dump); } } CERTIFY(analyzer, ANALYZER); FullTextType_init(loaded, analyzer); DECREF(analyzer); if (boost_dump) { loaded->boost = boost; } if (indexed_dump) { loaded->indexed = indexed; } if (stored_dump) { loaded->stored = stored; } if (sort_dump) { loaded->sortable = sortable; } if (hl_dump) { loaded->highlightable = hl; } return loaded; }
StringType* StringType_load(StringType *self, Obj *dump) { Hash *source = (Hash*)CERTIFY(dump, HASH); CharBuf *class_name = (CharBuf*)Hash_Fetch_Str(source, "_class", 6); VTable *vtable = (class_name != NULL && Obj_Is_A((Obj*)class_name, CHARBUF)) ? VTable_singleton(class_name, NULL) : STRINGTYPE; StringType *loaded = (StringType*)VTable_Make_Obj(vtable); Obj *boost_dump = Hash_Fetch_Str(source, "boost", 5); Obj *indexed_dump = Hash_Fetch_Str(source, "indexed", 7); Obj *stored_dump = Hash_Fetch_Str(source, "stored", 6); Obj *sortable_dump = Hash_Fetch_Str(source, "sortable", 8); UNUSED_VAR(self); StringType_init(loaded); if (boost_dump) { loaded->boost = (float)Obj_To_F64(boost_dump); } if (indexed_dump) { loaded->indexed = (bool_t)Obj_To_I64(indexed_dump); } if (stored_dump) { loaded->stored = (bool_t)Obj_To_I64(stored_dump); } if (sortable_dump) { loaded->sortable = (bool_t)Obj_To_I64(sortable_dump); } return loaded; }
bool_t StandardTokenizer_equals(StandardTokenizer *self, Obj *other) { StandardTokenizer *const twin = (StandardTokenizer*)other; if (twin == self) { return true; } if (!Obj_Is_A(other, STANDARDTOKENIZER)) { return false; } return true; }
bool WhitespaceTokenizer_Equals_IMP(WhitespaceTokenizer *self, Obj *other) { WhitespaceTokenizer *const twin = (WhitespaceTokenizer*)other; if (twin == self) { return true; } if (!Obj_Is_A(other, WHITESPACETOKENIZER)) { return false; } return true; }
BlobType* BlobType_Load_IMP(BlobType *self, Obj *dump) { Hash *source = (Hash*)CERTIFY(dump, HASH); String *class_name = (String*)Hash_Fetch_Utf8(source, "_class", 6); VTable *vtable = (class_name != NULL && Obj_Is_A((Obj*)class_name, STRING)) ? VTable_singleton(class_name, NULL) : BLOBTYPE; BlobType *loaded = (BlobType*)VTable_Make_Obj(vtable); Obj *boost_dump = Hash_Fetch_Utf8(source, "boost", 5); Obj *indexed_dump = Hash_Fetch_Utf8(source, "indexed", 7); Obj *stored_dump = Hash_Fetch_Utf8(source, "stored", 6); UNUSED_VAR(self); BlobType_init(loaded, false); BlobTypeIVARS *const loaded_ivars = BlobType_IVARS(loaded); if (boost_dump) { loaded_ivars->boost = (float)Obj_To_F64(boost_dump); } if (indexed_dump) { loaded_ivars->indexed = Obj_To_Bool(indexed_dump); } if (stored_dump){ loaded_ivars->stored = Obj_To_Bool(stored_dump); } return loaded; }
bool_t Hash_equals(Hash *self, Obj *other) { Hash *twin = (Hash*)other; Obj *key; Obj *val; if (twin == self) { return true; } if (!Obj_Is_A(other, HASH)) { return false; } if (self->size != twin->size) { return false; } Hash_Iterate(self); while (Hash_Next(self, &key, &val)) { Obj *other_val = Hash_Fetch(twin, key); if (!other_val || !Obj_Equals(other_val, val)) { return false; } } return true; }
bool_t RAMFolder_local_is_directory(RAMFolder *self, const CharBuf *name) { Obj *entry = Hash_Fetch(self->entries, (Obj*)name); if (entry && Obj_Is_A(entry, FOLDER)) { return true; } return false; }
Matcher* NOTCompiler_make_matcher(NOTCompiler *self, SegReader *reader, bool need_score) { NOTCompilerIVARS *const ivars = NOTCompiler_IVARS(self); Compiler *negated_compiler = (Compiler*)CERTIFY(VA_Fetch(ivars->children, 0), COMPILER); Matcher *negated_matcher = Compiler_Make_Matcher(negated_compiler, reader, false); UNUSED_VAR(need_score); if (negated_matcher == NULL) { float weight = NOTCompiler_Get_Weight(self); int32_t doc_max = SegReader_Doc_Max(reader); return (Matcher*)MatchAllMatcher_new(weight, doc_max); } else if (Obj_Is_A((Obj*)negated_matcher, MATCHALLMATCHER)) { DECREF(negated_matcher); return NULL; } else { int32_t doc_max = SegReader_Doc_Max(reader); Matcher *retval = (Matcher*)NOTMatcher_new(negated_matcher, doc_max); DECREF(negated_matcher); return retval; } }
NumericType* NumType_load(NumericType *self, Obj *dump) { UNUSED_VAR(self); Hash *source = (Hash*)CERTIFY(dump, HASH); // Get a VTable CharBuf *class_name = (CharBuf*)Hash_Fetch_Str(source, "_class", 6); CharBuf *type_spec = (CharBuf*)Hash_Fetch_Str(source, "type", 4); VTable *vtable = NULL; if (class_name != NULL && Obj_Is_A((Obj*)class_name, CHARBUF)) { vtable = VTable_singleton(class_name, NULL); } else if (type_spec != NULL && Obj_Is_A((Obj*)type_spec, CHARBUF)) { if (CB_Equals_Str(type_spec, "i32_t", 5)) { vtable = INT32TYPE; } else if (CB_Equals_Str(type_spec, "i64_t", 5)) { vtable = INT64TYPE; } else if (CB_Equals_Str(type_spec, "f32_t", 5)) { vtable = FLOAT32TYPE; } else if (CB_Equals_Str(type_spec, "f64_t", 5)) { vtable = FLOAT64TYPE; } else { THROW(ERR, "Unrecognized type string: '%o'", type_spec); } } CERTIFY(vtable, VTABLE); NumericType *loaded = (NumericType*)VTable_Make_Obj(vtable); // Extract boost. Obj *boost_dump = Hash_Fetch_Str(source, "boost", 5); float boost = boost_dump ? (float)Obj_To_F64(boost_dump) : 1.0f; // Find boolean properties. Obj *indexed_dump = Hash_Fetch_Str(source, "indexed", 7); Obj *stored_dump = Hash_Fetch_Str(source, "stored", 6); Obj *sort_dump = Hash_Fetch_Str(source, "sortable", 8); bool_t indexed = indexed_dump ? (bool_t)Obj_To_I64(indexed_dump) : true; bool_t stored = stored_dump ? (bool_t)Obj_To_I64(stored_dump) : true; bool_t sortable = sort_dump ? (bool_t)Obj_To_I64(sort_dump) : false; return NumType_init2(loaded, boost, indexed, stored, sortable); }
bool LFLock_Maybe_Delete_File_IMP(LockFileLock *self, String *path, bool delete_mine, bool delete_other) { LockFileLockIVARS *const ivars = LFLock_IVARS(self); Folder *folder = ivars->folder; bool success = false; // Only delete locks that start with our lock name. if (!Str_Starts_With_Utf8(path, "locks", 5)) { return false; } StringIterator *iter = Str_Top(path); StrIter_Advance(iter, 5 + 1); if (!StrIter_Starts_With(iter, ivars->name)) { DECREF(iter); return false; } DECREF(iter); // Attempt to delete dead lock file. if (Folder_Exists(folder, path)) { Hash *hash = (Hash*)Json_slurp_json(folder, path); if (hash != NULL && Obj_Is_A((Obj*)hash, HASH)) { String *pid_buf = (String*)Hash_Fetch_Utf8(hash, "pid", 3); String *host = (String*)Hash_Fetch_Utf8(hash, "host", 4); String *name = (String*)Hash_Fetch_Utf8(hash, "name", 4); // Match hostname and lock name. if (host != NULL && Str_Is_A(host, STRING) && Str_Equals(host, (Obj*)ivars->host) && name != NULL && Str_Is_A(name, STRING) && Str_Equals(name, (Obj*)ivars->name) && pid_buf != NULL && Str_Is_A(pid_buf, STRING) ) { // Verify that pid is either mine or dead. int pid = (int)Str_To_I64(pid_buf); if ((delete_mine && pid == PID_getpid()) // This process. || (delete_other && !PID_active(pid)) // Dead pid. ) { if (Folder_Delete(folder, path)) { success = true; } else { String *mess = MAKE_MESS("Can't delete '%o'", path); DECREF(hash); Err_throw_mess(ERR, mess); } } } } DECREF(hash); } return success; }
bool_t Normalizer_equals(Normalizer *self, Obj *other) { Normalizer *const twin = (Normalizer*)other; if (twin == self) { return true; } if (!Obj_Is_A(other, NORMALIZER)) { return false; } if (twin->options != self->options) { return false; } return true; }
bool BlobType_Equals_IMP(BlobType *self, Obj *other) { if ((BlobType*)other == self) { return true; } if (!Obj_Is_A(other, BLOBTYPE)) { return false; } BlobType_Equals_t super_equals = (BlobType_Equals_t)SUPER_METHOD_PTR(BLOBTYPE, LUCY_BlobType_Equals); return super_equals(self, other); }
bool_t NoMatchQuery_equals(NoMatchQuery *self, Obj *other) { NoMatchQuery *twin = (NoMatchQuery*)other; if (!Obj_Is_A(other, NOMATCHQUERY)) { return false; } if (self->boost != twin->boost) { return false; } if (!!self->fails_to_match != !!twin->fails_to_match) { return false; } return true; }
bool ORQuery_Equals_IMP(ORQuery *self, Obj *other) { if ((ORQuery*)other == self) { return true; } if (!Obj_Is_A(other, ORQUERY)) { return false; } ORQuery_Equals_t super_equals = (ORQuery_Equals_t)SUPER_METHOD_PTR(ORQUERY, LUCY_ORQuery_Equals); return super_equals(self, other); }
bool_t PolyAnalyzer_equals(PolyAnalyzer *self, Obj *other) { PolyAnalyzer *const twin = (PolyAnalyzer*)other; if (twin == self) { return true; } if (!Obj_Is_A(other, POLYANALYZER)) { return false; } if (!VA_Equals(twin->analyzers, (Obj*)self->analyzers)) { return false; } return true; }
bool Doc_Equals_IMP(Doc *self, Obj *other) { if ((Doc*)other == self) { return true; } if (!Obj_Is_A(other, DOC)) { return false; } DocIVARS *const ivars = Doc_IVARS(self); DocIVARS *const ovars = Doc_IVARS((Doc*)other); return Hash_Equals((Hash*)ivars->fields, (Obj*)ovars->fields); }
InStream* InStream_do_open(InStream *self, Obj *file) { InStreamIVARS *const ivars = InStream_IVARS(self); // Init. ivars->buf = NULL; ivars->limit = NULL; ivars->offset = 0; ivars->window = FileWindow_new(); // Obtain a FileHandle. if (Obj_Is_A(file, FILEHANDLE)) { ivars->file_handle = (FileHandle*)INCREF(file); } else if (Obj_Is_A(file, RAMFILE)) { ivars->file_handle = (FileHandle*)RAMFH_open(NULL, FH_READ_ONLY, (RAMFile*)file); } else if (Obj_Is_A(file, CHARBUF)) { ivars->file_handle = (FileHandle*)FSFH_open((CharBuf*)file, FH_READ_ONLY); } else { Err_set_error(Err_new(CB_newf("Invalid type for param 'file': '%o'", Obj_Get_Class_Name(file)))); DECREF(self); return NULL; } if (!ivars->file_handle) { ERR_ADD_FRAME(Err_get_error()); DECREF(self); return NULL; } // Get length and filename from the FileHandle. ivars->filename = CB_Clone(FH_Get_Path(ivars->file_handle)); ivars->len = FH_Length(ivars->file_handle); if (ivars->len == -1) { ERR_ADD_FRAME(Err_get_error()); DECREF(self); return NULL; } return self; }
bool_t Int64Type_equals(Int64Type *self, Obj *other) { if (self == (Int64Type*)other) { return true; } if (!other) { return false; } if (!Obj_Is_A(other, INT64TYPE)) { return false; } Int64Type_Equals_t super_equals = SUPER_METHOD_PTR(INT64TYPE, Lucy_Int64Type_Equals); return super_equals(self, other); }
bool Num_equals(Num *self, Obj *other) { Num *twin = (Num*)other; if (twin == self) { return true; } if (!Obj_Is_A(other, NUM)) { return false; } if (Num_To_F64(self) != Num_To_F64(twin)) { return false; } if (Num_To_I64(self) != Num_To_I64(twin)) { return false; } return true; }
bool EasyAnalyzer_equals(EasyAnalyzer *self, Obj *other) { if ((EasyAnalyzer*)other == self) { return true; } if (!Obj_Is_A(other, EASYANALYZER)) { return false; } EasyAnalyzerIVARS *const ivars = EasyAnalyzer_IVARS(self); EasyAnalyzerIVARS *const ovars = EasyAnalyzer_IVARS((EasyAnalyzer*)other); if (!CB_Equals(ovars->language, (Obj*)ivars->language)) { return false; } return true; }
bool RegexTokenizer_Equals_IMP(RegexTokenizer *self, Obj *other) { if ((RegexTokenizer*)other == self) { return true; } if (!Obj_Is_A(other, REGEXTOKENIZER)) { return false; } RegexTokenizerIVARS *ivars = RegexTokenizer_IVARS(self); RegexTokenizerIVARS *ovars = RegexTokenizer_IVARS((RegexTokenizer*)other); if (!Str_Equals(ivars->pattern, (Obj*)ovars->pattern)) { return false; } return true; }
bool PolyAnalyzer_Equals_IMP(PolyAnalyzer *self, Obj *other) { if ((PolyAnalyzer*)other == self) { return true; } if (!Obj_Is_A(other, POLYANALYZER)) { return false; } PolyAnalyzerIVARS *const ivars = PolyAnalyzer_IVARS(self); PolyAnalyzerIVARS *const ovars = PolyAnalyzer_IVARS((PolyAnalyzer*)other); if (!VA_Equals(ovars->analyzers, (Obj*)ivars->analyzers)) { return false; } return true; }
bool_t Float32Type_equals(Float32Type *self, Obj *other) { if (self == (Float32Type*)other) { return true; } if (!other) { return false; } if (!Obj_Is_A(other, FLOAT32TYPE)) { return false; } Float32Type_Equals_t super_equals = SUPER_METHOD_PTR(FLOAT32TYPE, Lucy_Float32Type_Equals); return super_equals(self, other); }
bool_t Int32Type_equals(Int32Type *self, Obj *other) { if (self == (Int32Type*)other) { return true; } if (!other) { return false; } if (!Obj_Is_A(other, INT32TYPE)) { return false; } Int32Type_equals_t super_equals = (Int32Type_equals_t) SUPER_METHOD(INT32TYPE, Int32Type, Equals); return super_equals(self, other); }