1 /*
2 * Copyright (C) 2008-2012 OMRON SOFTWARE Co., Ltd.
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 * http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 */
16
17 #include "nj_lib.h"
18 #include "nj_err.h"
19 #include "nj_ext.h"
20 #include "nj_dic.h"
21 #include "njd.h"
22 #ifdef NJ_LEARN_MUHENKAN_DEBUG
23 #include <stdio.h>
24 #include <def_mojicode.h>
25 #endif
26 #ifdef NJ_AWNN22_DEBUG
27 #include <stdio.h>
28 #include <def_mojicode.h>
29 #endif
30
31 #define QUE_TYPE_EMPTY 0
32 #define QUE_TYPE_NEXT 0
33 #define QUE_TYPE_JIRI 1
34 #define QUE_TYPE_FZK 2
35 #define POS_DATA_OFFSET 0x20
36 #define POS_LEARN_WORD 0x24
37 #define POS_MAX_WORD 0x28
38 #define POS_QUE_SIZE 0x2C
39 #define POS_NEXT_QUE 0x30
40 #define POS_WRITE_FLG 0x34
41 #define POS_INDEX_OFFSET 0x3C
42 #define POS_INDEX_OFFSET2 0x40
43
44 #define LEARN_INDEX_TOP_ADDR(x) ((x) + (NJ_INT32_READ((x) + POS_INDEX_OFFSET)))
45 #define LEARN_INDEX_TOP_ADDR2(x) ((x) + (NJ_INT32_READ((x) + POS_INDEX_OFFSET2)))
46 #define LEARN_DATA_TOP_ADDR(x) ((x) + (NJ_INT32_READ((x) + POS_DATA_OFFSET)))
47
48 #define LEARN_INDEX_BOTTOM_ADDR(x) (LEARN_DATA_TOP_ADDR(x) - 1)
49
50 #define LEARN_QUE_STRING_OFFSET 5
51
52 #define ADDRESS_TO_POS(x,adr) (((adr) - LEARN_DATA_TOP_ADDR(x)) / QUE_SIZE(x))
53 #define POS_TO_ADDRESS(x,pos) (LEARN_DATA_TOP_ADDR(x) + QUE_SIZE(x) * (pos))
54
55 #define GET_UINT16(ptr) ((((NJ_UINT16)(*(ptr))) << 8) | (*((ptr) + 1) & 0x00ff))
56
57 #define GET_FPOS_FROM_DATA(x) ((NJ_UINT16)NJ_INT16_READ((x)+1) >> 7)
58 #define GET_YSIZE_FROM_DATA(x) ((NJ_UINT8)((NJ_UINT16)NJ_INT16_READ((x)+1) & 0x7F))
59 #define GET_BPOS_FROM_DATA(x) ((NJ_UINT16)NJ_INT16_READ((x)+3) >> 7)
60 #define GET_KSIZE_FROM_DATA(x) ((NJ_UINT8)((NJ_UINT16)NJ_INT16_READ((x)+3) & 0x7F))
61 #define GET_BPOS_FROM_EXT_DATA(x) ((NJ_UINT16)NJ_INT16_READ(x) >> 7)
62 #define GET_YSIZE_FROM_EXT_DATA(x) ((NJ_UINT8)((NJ_UINT16)NJ_INT16_READ(x) & 0x7F))
63
64 #define SET_BPOS_AND_YSIZE(x,bpos,ysize) \
65 NJ_INT16_WRITE((x), ((NJ_UINT16)((bpos) << 7) | ((ysize) & 0x7F)))
66 #define SET_FPOS_AND_YSIZE(x,fpos,ysize) \
67 NJ_INT16_WRITE(((x)+1), ((NJ_UINT16)((fpos) << 7) | ((ysize) & 0x7F)))
68 #define SET_BPOS_AND_KSIZE(x,bpos,ksize) \
69 NJ_INT16_WRITE(((x)+3), ((NJ_UINT16)((bpos) << 7) | ((ksize) & 0x7F)))
70
71 #define GET_TYPE_FROM_DATA(x) (*(x) & 0x03)
72 #define GET_UFLG_FROM_DATA(x) (*(x) >> 7)
73 #define GET_FFLG_FROM_DATA(x) ((*(x) >> 6) & 0x01)
74 #define GET_MFLG_FROM_DATA(x) (*(x) & 0x10)
75
76 #define SET_TYPE_UFLG_FFLG(x,type,u,f) \
77 (*(x) = (NJ_UINT8)(((type) & 0x03) | \
78 (((u) & 0x01) << 7) | (((f) & 0x01) << 6)))
79 #define SET_TYPE_ALLFLG(x,type,u,f,m) \
80 (*(x) = (NJ_UINT8)(((type) & 0x03) | \
81 (((u) & 0x01) << 7) | (((f) & 0x01) << 6) | (((m) & 0x01) << 4)))
82
83 #define RESET_FFLG(x) (*(x) &= 0xbf)
84
85 #define STATE_COPY(to, from) \
86 { ((NJ_UINT8*)(to))[0] = ((NJ_UINT8*)(from))[0]; \
87 ((NJ_UINT8*)(to))[1] = ((NJ_UINT8*)(from))[1]; \
88 ((NJ_UINT8*)(to))[2] = ((NJ_UINT8*)(from))[2]; \
89 ((NJ_UINT8*)(to))[3] = ((NJ_UINT8*)(from))[3]; }
90
91 #define USE_QUE_NUM(que_size, str_size) \
92 ( (((str_size) % ((que_size) - 1)) == 0) \
93 ? ((str_size) / ((que_size) - 1)) \
94 : ((str_size) / ((que_size) - 1) + 1) )
95
96 #define NEXT_QUE(que, max) ( ((que) < ((max) - 1)) ? ((que) + 1) : 0 )
97
98 #define PREV_QUE(que, max) ( ((que) == 0) ? ((max) - 1) : ((que) - 1) )
99
100 #define COPY_QUE(handle, src, dst) \
101 nj_memcpy(POS_TO_ADDRESS((handle), (dst)), POS_TO_ADDRESS((handle), (src)), QUE_SIZE(handle))
102
103
104 #define INIT_HINDO (-10000)
105
106 #define LOC_CURRENT_NO_ENTRY 0xffffffffU
107
108
109
110 static NJ_WQUE *get_que(NJ_CLASS *iwnn, NJ_DIC_HANDLE handle, NJ_UINT16 que_id);
111 static NJ_INT16 is_continued(NJ_CLASS *iwnn, NJ_DIC_HANDLE handle, NJ_UINT16 que_id);
112 static NJ_UINT16 search_next_que(NJ_DIC_HANDLE handle, NJ_UINT16 que_id);
113 static NJ_INT16 que_strcmp_complete_with_hyouki(NJ_CLASS *iwnn, NJ_DIC_HANDLE handle, NJ_UINT16 que_id, NJ_CHAR *yomi, NJ_UINT16 yomi_len, NJ_CHAR *hyouki, NJ_UINT8 multi_flg);
114 static NJ_CHAR *get_string(NJ_CLASS *iwnn, NJ_DIC_HANDLE handle, NJ_UINT16 que_id, NJ_UINT8 *slen);
115 static NJ_CHAR *get_hyouki(NJ_CLASS *iwnn, NJ_DIC_HANDLE handle, NJ_UINT16 que_id, NJ_UINT8 *slen);
116 static NJ_INT16 get_cand_by_sequential(NJ_CLASS *iwnn, NJ_SEARCH_CONDITION *cond, NJ_SEARCH_LOCATION_SET *loctset, NJ_UINT8 search_pattern, NJ_UINT8 comp_flg);
117 static NJ_INT16 get_cand_by_evaluate(NJ_CLASS *iwnn, NJ_SEARCH_CONDITION *cond, NJ_SEARCH_LOCATION_SET *loctset, NJ_UINT8 search_pattern);
118 static NJ_INT16 get_cand_by_evaluate2(NJ_CLASS *iwnn, NJ_SEARCH_CONDITION *cond, NJ_SEARCH_LOCATION_SET *loctset, NJ_UINT8 search_pattern, NJ_UINT16 hIdx);
119 static NJ_INT16 search_range_by_yomi(NJ_CLASS *iwnn, NJ_DIC_HANDLE handle, NJ_UINT8 op, NJ_CHAR *yomi, NJ_UINT16 ylen, NJ_UINT16 *from, NJ_UINT16 *to, NJ_UINT8 *forward_flag);
120 static NJ_INT16 search_range_by_yomi2(NJ_CLASS *iwnn, NJ_DIC_HANDLE handle, NJ_UINT8 op, NJ_CHAR *yomi, NJ_UINT16 ylen, NJ_UINT16 sfrom, NJ_UINT16 sto, NJ_UINT16 *from, NJ_UINT16 *to,
121 NJ_UINT8 *forward_flag);
122 static NJ_INT16 search_range_by_yomi_multi(NJ_CLASS *iwnn, NJ_DIC_HANDLE handle, NJ_CHAR *yomi, NJ_UINT16 ylen, NJ_UINT16 *from, NJ_UINT16 *to);
123 static NJ_INT16 str_que_cmp(NJ_CLASS *iwnn, NJ_DIC_HANDLE handle, NJ_CHAR *yomi, NJ_UINT16 yomiLen, NJ_UINT16 que_id, NJ_UINT8 mode);
124 static NJ_WQUE *get_que_type_and_next(NJ_CLASS *iwnn, NJ_DIC_HANDLE handle, NJ_UINT16 que_id);
125 static NJ_WQUE *get_que_allHinsi(NJ_CLASS *iwnn, NJ_DIC_HANDLE handle, NJ_UINT16 que_id);
126 static NJ_WQUE *get_que_yomiLen_and_hyoukiLen(NJ_CLASS *iwnn, NJ_DIC_HANDLE handle, NJ_UINT16 que_id);
127 static NJ_INT16 continue_cnt(NJ_CLASS *iwnn, NJ_DIC_HANDLE handle, NJ_UINT16 que_id);
128
129 static NJ_UINT8 *get_search_index_address(NJ_DIC_HANDLE handle, NJ_UINT8 search_pattern);
130
131 static NJ_HINDO get_hindo(NJ_CLASS *iwnn, NJ_SEARCH_LOCATION_SET *loctset, NJ_UINT8 search_pattern);
132
133 static NJ_HINDO calculate_hindo(NJ_DIC_HANDLE handle, NJ_INT32 freq, NJ_DIC_FREQ *dic_freq, NJ_INT16 freq_max, NJ_INT16 freq_min);
134 static NJ_INT16 que_strcmp_include(NJ_CLASS *iwnn, NJ_DIC_HANDLE handle, NJ_UINT16 que_id, NJ_CHAR *yomi);
135
136 #define GET_LEARN_MAX_WORD_COUNT(h) ((NJ_UINT16)NJ_INT32_READ((h) + POS_MAX_WORD))
137
138 #define GET_LEARN_WORD_COUNT(h) \
139 ((NJ_UINT16)NJ_INT32_READ((h) + POS_LEARN_WORD))
140 #define SET_LEARN_WORD_COUNT(h, n) \
141 NJ_INT32_WRITE((h)+POS_LEARN_WORD, (NJ_UINT32)(n))
142 #define GET_LEARN_NEXT_WORD_POS(h) \
143 ((NJ_UINT16)NJ_INT32_READ((h) + POS_NEXT_QUE))
144 #define SET_LEARN_NEXT_WORD_POS(h, id) \
145 NJ_INT32_WRITE((h)+POS_NEXT_QUE, (NJ_UINT32)(id))
146 #define QUE_SIZE(h) ((NJ_UINT16)NJ_INT32_READ((h) + POS_QUE_SIZE))
147
148 #define COPY_UINT16(dst,src) (*(NJ_UINT16 *)(dst) = *(NJ_UINT16 *)(src))
149
get_search_index_address(NJ_DIC_HANDLE handle,NJ_UINT8 search_pattern)150 static NJ_UINT8 *get_search_index_address(NJ_DIC_HANDLE handle, NJ_UINT8 search_pattern) {
151
152
153
154 return LEARN_INDEX_TOP_ADDR(handle);
155 }
156
njd_l_search_word(NJ_CLASS * iwnn,NJ_SEARCH_CONDITION * con,NJ_SEARCH_LOCATION_SET * loctset,NJ_UINT8 comp_flg)157 NJ_INT16 njd_l_search_word(NJ_CLASS *iwnn, NJ_SEARCH_CONDITION *con,
158 NJ_SEARCH_LOCATION_SET *loctset,
159 NJ_UINT8 comp_flg) {
160
161 NJ_UINT16 word_count;
162 NJ_UINT32 type;
163 NJ_DIC_INFO *pdicinfo;
164 NJ_UINT16 hIdx;
165 NJ_INT16 ret;
166
167
168 word_count = GET_LEARN_WORD_COUNT(loctset->loct.handle);
169 if (word_count == 0) {
170
171 loctset->loct.status = NJ_ST_SEARCH_END_EXT;
172 return 0;
173 }
174
175 type = NJ_GET_DIC_TYPE_EX(loctset->loct.type, loctset->loct.handle);
176
177 if (type == NJ_DIC_TYPE_CUSTOM_INCOMPRESS) {
178 if ((con->operation == NJ_CUR_OP_COMP) ||
179 (con->operation == NJ_CUR_OP_FORE)){
180
181 if (con->ylen > NJ_GET_MAX_YLEN(loctset->loct.handle)) {
182 loctset->loct.status = NJ_ST_SEARCH_END_EXT;
183 return 0;
184 }
185 }
186 }
187
188
189 switch (con->operation) {
190 case NJ_CUR_OP_COMP:
191 if (con->mode != NJ_CUR_MODE_FREQ) {
192
193 loctset->loct.status = NJ_ST_SEARCH_END_EXT;
194 break;
195 }
196
197
198 return get_cand_by_sequential(iwnn, con, loctset, con->operation, comp_flg);
199
200 case NJ_CUR_OP_FORE:
201
202 if (con->mode == NJ_CUR_MODE_YOMI) {
203
204 return get_cand_by_sequential(iwnn, con, loctset, con->operation, 0);
205 } else {
206
207
208 pdicinfo = con->ds->dic;
209 for (hIdx = 0; (hIdx < NJ_MAX_DIC) && (pdicinfo->handle != loctset->loct.handle); hIdx++) {
210 pdicinfo++;
211 }
212
213 if (hIdx == NJ_MAX_DIC) {
214
215 loctset->loct.status = NJ_ST_SEARCH_END;
216 return 0;
217 }
218
219
220
221 if ((con->ds->dic[hIdx].srhCache == NULL) || (con->ylen == 0) ||
222 !(con->ds->mode & 0x0001)) {
223 return get_cand_by_evaluate(iwnn, con, loctset, con->operation);
224 } else {
225 ret = get_cand_by_evaluate2(iwnn, con, loctset, con->operation, hIdx);
226 if (ret == NJ_SET_ERR_VAL(NJ_FUNC_SEARCH_RANGE_BY_YOMI, NJ_ERR_CACHE_NOT_ENOUGH)) {
227
228 NJ_SET_CACHEOVER_TO_SCACHE(con->ds->dic[hIdx].srhCache);
229 ret = get_cand_by_evaluate2(iwnn, con, loctset, con->operation, hIdx);
230 }
231 return ret;
232 }
233 }
234
235 case NJ_CUR_OP_LINK:
236
237 if (NJ_GET_DIC_TYPE_EX(loctset->loct.type, loctset->loct.handle) == NJ_DIC_TYPE_USER) {
238
239 loctset->loct.status = NJ_ST_SEARCH_END_EXT;
240 break;
241 }
242 if (con->mode != NJ_CUR_MODE_FREQ) {
243
244 loctset->loct.status = NJ_ST_SEARCH_END_EXT;
245 break;
246 }
247
248 if (comp_flg == 0) {
249
250 return get_cand_by_sequential(iwnn, con, loctset, con->operation, 0);
251 } else {
252
253 return get_cand_by_evaluate(iwnn, con, loctset, con->operation);
254 }
255
256 default:
257 loctset->loct.status = NJ_ST_SEARCH_END_EXT;
258 }
259
260 return 0;
261 }
262
get_que_type_and_next(NJ_CLASS * iwnn,NJ_DIC_HANDLE handle,NJ_UINT16 que_id)263 static NJ_WQUE *get_que_type_and_next(NJ_CLASS *iwnn, NJ_DIC_HANDLE handle,
264 NJ_UINT16 que_id) {
265 NJ_UINT8 *ptr;
266 NJ_WQUE *que = &(iwnn->que_tmp);
267
268
269 if (que_id >= GET_LEARN_MAX_WORD_COUNT(handle)) {
270 return NULL;
271 }
272
273 ptr = POS_TO_ADDRESS(handle, que_id);
274
275 que->type = GET_TYPE_FROM_DATA(ptr);
276 que->next_flag = GET_FFLG_FROM_DATA(ptr);
277
278 switch (que->type) {
279 case QUE_TYPE_EMPTY:
280 case QUE_TYPE_JIRI:
281 case QUE_TYPE_FZK:
282 return que;
283 default:
284 break;
285 }
286 #ifdef LEARN_DEBUG
287 printf("FATAL : Illegal que was gotten (que_id=%d)\n", que_id);
288 #endif
289 return NULL;
290 }
291
get_que_yomiLen_and_hyoukiLen(NJ_CLASS * iwnn,NJ_DIC_HANDLE handle,NJ_UINT16 que_id)292 static NJ_WQUE *get_que_yomiLen_and_hyoukiLen(NJ_CLASS *iwnn, NJ_DIC_HANDLE handle,
293 NJ_UINT16 que_id) {
294 NJ_UINT8 *ptr;
295 NJ_WQUE *que = &(iwnn->que_tmp);
296
297
298 if (que_id >= GET_LEARN_MAX_WORD_COUNT(handle)) {
299 return NULL;
300 }
301
302 ptr = POS_TO_ADDRESS(handle, que_id);
303
304 que->type = GET_TYPE_FROM_DATA(ptr);
305 que->yomi_byte = GET_YSIZE_FROM_DATA(ptr);
306 que->yomi_len = que->yomi_byte / sizeof(NJ_CHAR);
307 que->hyouki_byte = GET_KSIZE_FROM_DATA(ptr);
308 que->hyouki_len = que->hyouki_byte / sizeof(NJ_CHAR);
309
310 switch (que->type) {
311 case QUE_TYPE_JIRI:
312 case QUE_TYPE_FZK:
313 return que;
314 default:
315 break;
316 }
317 #ifdef LEARN_DEBUG
318 printf("FATAL : Illegal que was gotten (que_id=%d)\n", que_id);
319 #endif
320 return NULL;
321 }
322
get_que_allHinsi(NJ_CLASS * iwnn,NJ_DIC_HANDLE handle,NJ_UINT16 que_id)323 static NJ_WQUE *get_que_allHinsi(NJ_CLASS *iwnn, NJ_DIC_HANDLE handle,
324 NJ_UINT16 que_id) {
325 NJ_UINT8 *ptr;
326 NJ_WQUE *que = &(iwnn->que_tmp);
327
328
329 if (que_id >= GET_LEARN_MAX_WORD_COUNT(handle)) {
330 return NULL;
331 }
332
333 ptr = POS_TO_ADDRESS(handle, que_id);
334
335 que->type = GET_TYPE_FROM_DATA(ptr);
336 que->mae_hinsi = GET_FPOS_FROM_DATA(ptr);
337 que->ato_hinsi = GET_BPOS_FROM_DATA(ptr);
338
339 switch (que->type) {
340 case QUE_TYPE_JIRI:
341 case QUE_TYPE_FZK:
342 return que;
343 default:
344 break;
345 }
346 #ifdef LEARN_DEBUG
347 printf("FATAL : Illegal que was gotten (que_id=%d)\n", que_id);
348 #endif
349 return NULL;
350 }
351
get_que(NJ_CLASS * iwnn,NJ_DIC_HANDLE handle,NJ_UINT16 que_id)352 static NJ_WQUE *get_que(NJ_CLASS *iwnn, NJ_DIC_HANDLE handle, NJ_UINT16 que_id) {
353 NJ_UINT8 *ptr;
354 NJ_WQUE *que = &(iwnn->que_tmp);
355
356
357 if (que_id >= GET_LEARN_MAX_WORD_COUNT(handle)) {
358 return NULL;
359 }
360
361 ptr = POS_TO_ADDRESS(handle, que_id);
362
363 que->entry = que_id;
364 que->type = GET_TYPE_FROM_DATA(ptr);
365 que->mae_hinsi = GET_FPOS_FROM_DATA(ptr);
366 que->ato_hinsi = GET_BPOS_FROM_DATA(ptr);
367 que->yomi_byte = GET_YSIZE_FROM_DATA(ptr);
368 que->yomi_len = que->yomi_byte / sizeof(NJ_CHAR);
369 que->hyouki_byte= GET_KSIZE_FROM_DATA(ptr);
370 que->hyouki_len = que->hyouki_byte / sizeof(NJ_CHAR);
371 que->next_flag = GET_FFLG_FROM_DATA(ptr);
372
373 switch (que->type) {
374 case QUE_TYPE_JIRI:
375 case QUE_TYPE_FZK:
376 return que;
377 default:
378 break;
379 }
380 #ifdef LEARN_DEBUG
381 printf("FATAL : Illegal que was gotten (que_id=%d)\n", que_id);
382 #endif
383 return NULL;
384 }
385
is_continued(NJ_CLASS * iwnn,NJ_DIC_HANDLE handle,NJ_UINT16 que_id)386 static NJ_INT16 is_continued(NJ_CLASS *iwnn, NJ_DIC_HANDLE handle, NJ_UINT16 que_id) {
387 NJ_WQUE *que;
388 NJ_UINT16 i;
389 NJ_UINT16 max, end;
390
391
392 max = GET_LEARN_MAX_WORD_COUNT(handle);
393 end = GET_LEARN_NEXT_WORD_POS(handle);
394
395 for (i = 0; i < max; i++) {
396 que_id++;
397 if (que_id >= GET_LEARN_MAX_WORD_COUNT(handle)) {
398
399 que_id = 0;
400 }
401
402
403 if (que_id == end) {
404
405 return 0;
406 }
407
408 que = get_que_type_and_next(iwnn, handle, que_id);
409 #ifdef IWNN_ERR_CHECK
410 if (iwnn->err_check_flg == 1) {
411 que = NULL;
412 }
413 #endif
414 if (que == NULL) {
415 return NJ_SET_ERR_VAL(NJ_FUNC_IS_CONTINUED, NJ_ERR_DIC_BROKEN);
416 }
417 if (que->type != QUE_TYPE_EMPTY) {
418
419 if (que->next_flag != 0) {
420
421 return 1;
422 } else {
423
424 return 0;
425 }
426 }
427 }
428
429
430 return 0;
431 }
432
continue_cnt(NJ_CLASS * iwnn,NJ_DIC_HANDLE handle,NJ_UINT16 que_id)433 static NJ_INT16 continue_cnt(NJ_CLASS *iwnn, NJ_DIC_HANDLE handle, NJ_UINT16 que_id) {
434 NJ_WQUE *que;
435 NJ_UINT16 i;
436 NJ_UINT16 max, end;
437 NJ_INT16 cnt = 0;
438
439
440 max = GET_LEARN_MAX_WORD_COUNT(handle);
441 end = GET_LEARN_NEXT_WORD_POS(handle);
442
443 for (i = 0; i < max; i++) {
444 que_id++;
445 if (que_id >= max) {
446
447 que_id = 0;
448 }
449
450
451 if (que_id == end) {
452
453 return cnt;
454 }
455
456 que = get_que_type_and_next(iwnn, handle, que_id);
457 if (que == NULL) {
458 return NJ_SET_ERR_VAL(NJ_FUNC_CONTINUE_CNT, NJ_ERR_DIC_BROKEN);
459 }
460 if (que->type != QUE_TYPE_EMPTY) {
461
462 if (que->next_flag != 0) {
463
464 cnt++;
465
466
467 if (cnt >= (NJD_MAX_CONNECT_CNT - 1)) {
468 return cnt;
469 }
470 } else {
471
472 return cnt;
473 }
474 }
475 }
476
477
478 return 0;
479 }
480
search_next_que(NJ_DIC_HANDLE handle,NJ_UINT16 que_id)481 static NJ_UINT16 search_next_que(NJ_DIC_HANDLE handle, NJ_UINT16 que_id) {
482 NJ_UINT16 max;
483 NJ_UINT16 i;
484
485
486 max = GET_LEARN_MAX_WORD_COUNT(handle);
487
488 for (i = 0; i < max; i++) {
489 que_id++;
490 if (que_id >= max) {
491
492 que_id = 0;
493 }
494
495 if (GET_TYPE_FROM_DATA(POS_TO_ADDRESS(handle, que_id)) != QUE_TYPE_EMPTY) {
496
497 return que_id;
498 }
499 }
500
501
502 return 0;
503 }
504
que_strcmp_complete_with_hyouki(NJ_CLASS * iwnn,NJ_DIC_HANDLE handle,NJ_UINT16 que_id,NJ_CHAR * yomi,NJ_UINT16 yomi_len,NJ_CHAR * hyouki,NJ_UINT8 multi_flg)505 static NJ_INT16 que_strcmp_complete_with_hyouki(NJ_CLASS *iwnn, NJ_DIC_HANDLE handle,
506 NJ_UINT16 que_id, NJ_CHAR *yomi, NJ_UINT16 yomi_len, NJ_CHAR *hyouki,
507 NJ_UINT8 multi_flg) {
508 NJ_CHAR *str;
509 NJ_INT16 ret;
510 NJ_UINT8 slen;
511 NJ_UINT16 hyouki_len;
512 NJ_UINT16 que_yomilen, que_hyoukilen;
513 NJ_INT16 que_count = 1;
514 NJ_INT16 cnt = 0;
515
516
517
518 hyouki_len = nj_strlen(hyouki);
519
520 if (multi_flg == 0) {
521
522 cnt = 1;
523 } else {
524
525
526 cnt = GET_LEARN_WORD_COUNT(handle);
527 }
528
529 while (cnt--) {
530 str = get_string(iwnn, handle, que_id, &slen);
531 if (str == NULL) {
532 return NJ_SET_ERR_VAL(NJ_FUNC_QUE_STRCMP_COMPLETE_WITH_HYOUKI,
533 NJ_ERR_DIC_BROKEN);
534 }
535 que_yomilen = slen;
536
537 ret = nj_strncmp(yomi, str, que_yomilen);
538 if (ret != 0) {
539
540 return 0;
541 }
542
543 str = get_hyouki(iwnn, handle, que_id, &slen);
544 if (str == NULL) {
545 return NJ_SET_ERR_VAL(NJ_FUNC_QUE_STRCMP_COMPLETE_WITH_HYOUKI,
546 NJ_ERR_DIC_BROKEN);
547 }
548 que_hyoukilen = slen;
549
550 ret = nj_strncmp(hyouki, str, que_hyoukilen);
551 if (ret != 0) {
552
553 return 0;
554 }
555
556 if ((yomi_len == que_yomilen) &&
557 (hyouki_len == que_hyoukilen)) {
558
559 return que_count;
560 }
561
562 if ((que_yomilen > yomi_len) ||
563 (que_hyoukilen > hyouki_len)) {
564
565 return 0;
566 }
567
568 ret = is_continued(iwnn, handle, que_id);
569 if (ret <= 0) {
570
571 return ret;
572 }
573
574
575 if (que_count >= (NJD_MAX_CONNECT_CNT - 1)) {
576
577 return 0;
578 }
579
580 yomi_len -= que_yomilen;
581 yomi += que_yomilen;
582
583 hyouki_len -= que_hyoukilen;
584 hyouki += que_hyoukilen;
585
586
587 que_id = search_next_que(handle, que_id);
588 que_count++;
589 }
590 return 0;
591 }
592
que_strcmp_include(NJ_CLASS * iwnn,NJ_DIC_HANDLE handle,NJ_UINT16 que_id,NJ_CHAR * yomi)593 static NJ_INT16 que_strcmp_include(NJ_CLASS *iwnn, NJ_DIC_HANDLE handle,
594 NJ_UINT16 que_id, NJ_CHAR *yomi) {
595 NJ_CHAR *str;
596 NJ_UINT16 que_len;
597 NJ_UINT16 yomi_len;
598 NJ_INT16 ret;
599 NJ_INT16 que_count = 1;
600 NJ_UINT16 i = 0;
601 NJ_UINT8 slen;
602
603
604 #ifdef LEARN_DEBUG
605 printf("que_strcmp_include(que_id=%d, yomi=[%s])\n", que_id, yomi);
606 #endif
607 yomi_len = nj_strlen(yomi);
608 if (yomi_len == 0) {
609 return que_count;
610 }
611
612 i = GET_LEARN_WORD_COUNT(handle);
613
614 while (--i) {
615
616
617 ret = is_continued(iwnn, handle, que_id);
618 if (ret < 0) {
619
620 return ret;
621 } else if (ret == 0) {
622
623 return que_count;
624 }
625
626
627 que_id = search_next_que(handle, que_id);
628
629 str = get_string(iwnn, handle, que_id, &slen);
630 #ifdef IWNN_ERR_CHECK
631 if (iwnn->err_check_flg == 2) {
632 str = NULL;
633 }
634 #endif
635 if (str == NULL) {
636 return NJ_SET_ERR_VAL(NJ_FUNC_QUE_STRCMP_INCLUDE, NJ_ERR_DIC_BROKEN);
637 }
638 que_len = slen;
639
640
641 if (que_len > yomi_len) {
642 #ifdef LEARN_DEBUG
643 printf(" >> mismatch [%s] (que_len > yomi_len)\n", str);
644 #endif
645 return que_count;
646 }
647
648
649 ret = nj_strncmp(yomi, str, que_len);
650 if (ret != 0) {
651 #ifdef LEARN_DEBUG
652 printf(" >> mismatch [%s]\n", str);
653 #endif
654
655 return que_count;
656 }
657
658
659 if (que_len == yomi_len) {
660 #ifdef LEARN_DEBUG
661 printf(" >> match! [%s](%d)\n", str, que_count);
662 #endif
663 return (que_count + 1);
664 }
665
666 que_count++;
667 if (que_count >= NJD_MAX_CONNECT_CNT) {
668
669 return que_count;
670 }
671
672
673 yomi_len -= que_len;
674 yomi += que_len;
675 }
676
677 return que_count;
678 }
679
get_string(NJ_CLASS * iwnn,NJ_DIC_HANDLE handle,NJ_UINT16 que_id,NJ_UINT8 * slen)680 static NJ_CHAR *get_string(NJ_CLASS *iwnn, NJ_DIC_HANDLE handle,
681 NJ_UINT16 que_id, NJ_UINT8 *slen) {
682 NJ_UINT8 *src, *dst;
683 NJ_UINT8 copy_size, size;
684 NJ_UINT8 i;
685 NJ_UINT8 *top_addr;
686 NJ_UINT8 *bottom_addr;
687 NJ_UINT16 que_size;
688
689
690 src = POS_TO_ADDRESS(handle, que_id);
691 switch (GET_TYPE_FROM_DATA(src)) {
692 case QUE_TYPE_JIRI:
693 case QUE_TYPE_FZK:
694 size = GET_YSIZE_FROM_DATA(src);
695 *slen = (NJ_UINT8)(size / sizeof(NJ_CHAR));
696 break;
697
698 default:
699 #ifdef LEARN_DEBUG
700 printf("get_string(handle=%p, que_id=%d) : broken que\n", handle, que_id);
701 #endif
702 return NULL;
703 }
704
705 if (NJ_GET_DIC_TYPE(handle) == NJ_DIC_TYPE_USER) {
706 if (*slen > NJ_MAX_USER_LEN) {
707 return NULL;
708 }
709 } else {
710 if (*slen > NJ_MAX_LEN) {
711 return NULL;
712 }
713 }
714
715
716 src += LEARN_QUE_STRING_OFFSET;
717
718 que_size = QUE_SIZE(handle);
719
720
721 copy_size = (NJ_UINT8)que_size - LEARN_QUE_STRING_OFFSET;
722 dst = (NJ_UINT8*)&(iwnn->learn_string_tmp[0]);
723 if (copy_size > size) {
724
725 copy_size = size;
726 }
727 for (i = 0; i < copy_size; i++) {
728 *dst++ = *src++;
729 }
730
731
732 top_addr = LEARN_DATA_TOP_ADDR(handle);
733 bottom_addr = top_addr;
734 bottom_addr += que_size * GET_LEARN_MAX_WORD_COUNT(handle) - 1;
735
736 while (size -= copy_size) {
737
738 if (src >= bottom_addr) {
739 src = top_addr;
740 }
741
742
743 if (*src != QUE_TYPE_NEXT) {
744 #ifdef LEARN_DEBUG
745 printf("FATAL: src que was broken(not QUE_TYPE_NEXT) [src=%x]\n", src);
746 #endif
747 return NULL;
748 }
749
750 src++;
751 if (size < que_size) {
752
753 copy_size = size;
754 } else {
755 copy_size = (NJ_UINT8)(que_size - 1);
756 }
757 for (i = 0; i < copy_size; i++) {
758 *dst++ = *src++;
759 }
760 }
761 iwnn->learn_string_tmp[*slen] = NJ_CHAR_NUL;
762
763 return &(iwnn->learn_string_tmp[0]);
764 }
765
get_hyouki(NJ_CLASS * iwnn,NJ_DIC_HANDLE handle,NJ_UINT16 que_id,NJ_UINT8 * slen)766 static NJ_CHAR *get_hyouki(NJ_CLASS *iwnn, NJ_DIC_HANDLE handle,
767 NJ_UINT16 que_id, NJ_UINT8 *slen) {
768 NJ_UINT8 *src, *dst;
769 NJ_WQUE *que;
770 NJ_UINT8 copy_size, size;
771 NJ_UINT8 i;
772 NJ_UINT8 *top_addr;
773 NJ_UINT8 *bottom_addr;
774 NJ_CHAR *hira;
775 NJ_UINT16 que_size;
776 NJ_UINT32 dictype;
777
778
779 que = get_que_yomiLen_and_hyoukiLen(iwnn, handle, que_id);
780 if (que == NULL) {
781 return NULL;
782 }
783
784 dictype = NJ_GET_DIC_TYPE(handle);
785 if (dictype == NJ_DIC_TYPE_USER) {
786 if (que->yomi_len > NJ_MAX_USER_LEN) {
787 return NULL;
788 }
789 if (que->hyouki_len > NJ_MAX_USER_KOUHO_LEN) {
790 return NULL;
791 }
792 } else {
793 if (que->yomi_len > NJ_MAX_LEN) {
794 return NULL;
795 }
796 if (que->hyouki_len > NJ_MAX_RESULT_LEN) {
797 return NULL;
798 }
799 }
800
801 src = POS_TO_ADDRESS(handle, que_id);
802
803 if (que->hyouki_len == 0) {
804 hira = get_string(iwnn, handle, que_id, slen);
805 if (hira == NULL) {
806 return NULL;
807 }
808
809 if (GET_MFLG_FROM_DATA(src) != 0) {
810 *slen = (NJ_UINT8)nje_convert_hira_to_kata(hira, &(iwnn->muhenkan_tmp[0]), *slen);
811 return &(iwnn->muhenkan_tmp[0]);
812 } else {
813 return hira;
814 }
815 }
816
817 src += LEARN_QUE_STRING_OFFSET;
818
819 que_size = QUE_SIZE(handle);
820
821
822 size = que->yomi_byte;
823 copy_size = (NJ_UINT8)que_size - LEARN_QUE_STRING_OFFSET;
824 dst = (NJ_UINT8*)&(iwnn->learn_string_tmp[0]);
825 if (copy_size > size) {
826
827 copy_size = size;
828 }
829
830
831 top_addr = LEARN_DATA_TOP_ADDR(handle);
832 bottom_addr = top_addr;
833 bottom_addr += que_size * GET_LEARN_MAX_WORD_COUNT(handle) - 1;
834
835 src += copy_size;
836 while (size -= copy_size) {
837
838
839 if (src >= bottom_addr) {
840 src = top_addr;
841 }
842
843
844 if (*src != QUE_TYPE_NEXT) {
845 #ifdef LEARN_DEBUG
846 printf("FATAL: src que was broken(not QUE_TYPE_NEXT) [src=%x]\n", src);
847 #endif
848 return NULL;
849 }
850
851 src++;
852 if (size < que_size) {
853
854 copy_size = size;
855 } else {
856 copy_size = (NJ_UINT8)(que_size - 1);
857 }
858 src += copy_size;
859 }
860
861
862
863 if (((src - top_addr) % que_size) == 0) {
864
865 if (src >= bottom_addr) {
866 src = top_addr;
867 }
868
869 if (*src++ != QUE_TYPE_NEXT) {
870 #ifdef LEARN_DEBUG
871 printf("FATAL: src que was broken(QUE_TYPE_NEXT) [src=%x]\n", src - 1);
872 #endif
873 return NULL;
874 }
875 }
876
877 size = que->hyouki_byte;
878
879
880 copy_size = (NJ_UINT8)(que_size);
881 copy_size -= (NJ_UINT8)((src - top_addr) % que_size);
882 if (copy_size > size) {
883
884 copy_size = size;
885 }
886 for (i = 0; i < copy_size; i++) {
887 *dst++ = *src++;
888 }
889
890 while (size -= copy_size) {
891
892
893 if (src >= bottom_addr) {
894 src = top_addr;
895 }
896
897
898 if (*src != QUE_TYPE_NEXT) {
899 #ifdef LEARN_DEBUG
900 printf("FATAL: src que was broken(not QUE_TYPE_NEXT) [src=%x]\n", src);
901 #endif
902 return NULL;
903 }
904
905 src++;
906 if (size < que_size) {
907
908 copy_size = size;
909 } else {
910 copy_size = (NJ_UINT8)(que_size - 1);
911 }
912
913 for (i = 0; i < copy_size; i++) {
914 *dst++ = *src++;
915 }
916 }
917
918 *slen = que->hyouki_len;
919 iwnn->learn_string_tmp[*slen] = NJ_CHAR_NUL;
920
921 return &(iwnn->learn_string_tmp[0]);
922 }
923
get_cand_by_sequential(NJ_CLASS * iwnn,NJ_SEARCH_CONDITION * cond,NJ_SEARCH_LOCATION_SET * loctset,NJ_UINT8 search_pattern,NJ_UINT8 comp_flg)924 static NJ_INT16 get_cand_by_sequential(NJ_CLASS *iwnn, NJ_SEARCH_CONDITION *cond,
925 NJ_SEARCH_LOCATION_SET *loctset, NJ_UINT8 search_pattern,
926 NJ_UINT8 comp_flg) {
927 NJ_UINT16 current, from, to;
928 NJ_UINT16 que_id;
929 NJ_UINT8 *ptr, *p;
930 NJ_INT16 ret, num_count;
931 NJ_CHAR *yomi;
932 NJ_WQUE *que;
933 NJ_UINT8 forward_flag = 0;
934
935
936
937 if (GET_LOCATION_STATUS(loctset->loct.status) == NJ_ST_SEARCH_NO_INIT) {
938
939 ret = search_range_by_yomi(iwnn, loctset->loct.handle, search_pattern,
940 cond->yomi, cond->ylen, &from, &to, &forward_flag);
941 if (ret < 0) {
942 return ret;
943 }
944 if (ret == 0) {
945 if (forward_flag) {
946 loctset->loct.status = NJ_ST_SEARCH_END;
947 } else {
948 loctset->loct.status = NJ_ST_SEARCH_END_EXT;
949 }
950 return 0;
951 }
952 loctset->loct.top = from;
953 loctset->loct.bottom = to;
954 current = from;
955 } else if (GET_LOCATION_STATUS(loctset->loct.status) == NJ_ST_SEARCH_READY) {
956
957 current = (NJ_UINT16)(loctset->loct.current + 1);
958 } else {
959 loctset->loct.status = NJ_ST_SEARCH_END;
960 return 0;
961 }
962
963
964 ptr = get_search_index_address(loctset->loct.handle, cond->operation);
965 p = ptr + (current * NJ_INDEX_SIZE);
966
967 while (current <= loctset->loct.bottom) {
968 que_id = GET_UINT16(p);
969 if (search_pattern == NJ_CUR_OP_COMP) {
970
971 ret = str_que_cmp(iwnn, loctset->loct.handle, cond->yomi, cond->ylen, que_id, 1);
972
973
974 if (ret == 2) {
975 ret = 0;
976 }
977 } else if (search_pattern == NJ_CUR_OP_FORE) {
978
979 ret = str_que_cmp(iwnn, loctset->loct.handle, cond->yomi, cond->ylen, que_id, 2);
980
981
982 if (ret == 2) {
983 ret = 0;
984 }
985 } else {
986
987
988
989 ret = que_strcmp_complete_with_hyouki(iwnn, loctset->loct.handle, que_id,
990 cond->yomi, cond->ylen, cond->kanji, 0);
991 }
992
993 if (ret < 0) {
994 return ret;
995 }
996 if (ret > 0) {
997 if (search_pattern == NJ_CUR_OP_LINK) {
998
999
1000 num_count = continue_cnt(iwnn, loctset->loct.handle, que_id);
1001 if (num_count < 0) {
1002
1003 return num_count;
1004 }
1005
1006
1007 if (num_count >= ret) {
1008
1009 loctset->loct.current_info = (NJ_UINT8)(((num_count + 1) << 4) | ret);
1010 loctset->loct.current = current;
1011 loctset->loct.status = NJ_ST_SEARCH_READY;
1012 loctset->cache_freq = get_hindo(iwnn, loctset, search_pattern);
1013 return 1;
1014 }
1015 } else {
1016
1017
1018
1019
1020
1021
1022 que = get_que_allHinsi(iwnn, loctset->loct.handle, que_id);
1023 if (njd_connect_test(cond, que->mae_hinsi, que->ato_hinsi)) {
1024
1025
1026 switch (NJ_GET_DIC_TYPE_EX(loctset->loct.type, loctset->loct.handle)) {
1027 case NJ_DIC_TYPE_CUSTOM_INCOMPRESS:
1028 if ((search_pattern == NJ_CUR_OP_COMP) && (comp_flg == 1)) {
1029 yomi = cond->yomi + cond->ylen;
1030 ret = que_strcmp_include(iwnn, loctset->loct.handle, que_id, yomi);
1031 if (ret < 0) {
1032 return ret;
1033 }
1034 }
1035 break;
1036 default:
1037 break;
1038 }
1039 loctset->loct.current = current;
1040 loctset->loct.status = NJ_ST_SEARCH_READY;
1041
1042 loctset->loct.current_info = (ret & 0x0f) << 4;
1043 loctset->cache_freq = get_hindo(iwnn, loctset, search_pattern);
1044 return 1;
1045 }
1046 }
1047 }
1048 p += NJ_INDEX_SIZE;
1049 current++;
1050 }
1051
1052
1053 loctset->loct.status = NJ_ST_SEARCH_END;
1054 return 0;
1055 }
1056
get_cand_by_evaluate(NJ_CLASS * iwnn,NJ_SEARCH_CONDITION * cond,NJ_SEARCH_LOCATION_SET * loctset,NJ_UINT8 search_pattern)1057 static NJ_INT16 get_cand_by_evaluate(NJ_CLASS *iwnn, NJ_SEARCH_CONDITION *cond,
1058 NJ_SEARCH_LOCATION_SET *loctset, NJ_UINT8 search_pattern) {
1059 NJ_UINT16 from, to, i;
1060 NJ_UINT16 que_id, oldest;
1061 NJ_UINT32 max_value, eval, current;
1062 NJ_UINT8 *ptr, *p;
1063 NJ_WQUE *que;
1064 NJ_INT16 ret, num_count;
1065 NJ_INT32 found = 0;
1066 NJ_UINT8 forward_flag = 0;
1067 NJ_INT32 is_first_search, is_better_freq;
1068
1069
1070
1071 ptr = get_search_index_address(loctset->loct.handle, cond->operation);
1072
1073
1074 oldest = GET_LEARN_NEXT_WORD_POS(loctset->loct.handle);
1075
1076
1077 current = 0;
1078 if (GET_LOCATION_STATUS(loctset->loct.status) == NJ_ST_SEARCH_NO_INIT) {
1079 if (search_pattern == NJ_CUR_OP_LINK) {
1080
1081
1082
1083 ret = search_range_by_yomi_multi(iwnn, loctset->loct.handle,
1084 cond->yomi, cond->ylen, &from, &to);
1085 } else {
1086
1087
1088 ret = search_range_by_yomi(iwnn, loctset->loct.handle, search_pattern,
1089 cond->yomi, cond->ylen, &from, &to, &forward_flag);
1090 }
1091 if (ret <= 0) {
1092 loctset->loct.status = NJ_ST_SEARCH_END;
1093 return ret;
1094 }
1095 loctset->loct.top = from;
1096 loctset->loct.bottom = to;
1097 is_first_search = 1;
1098 } else if (GET_LOCATION_STATUS(loctset->loct.status) == NJ_ST_SEARCH_READY) {
1099 current = GET_UINT16(ptr + (loctset->loct.current * NJ_INDEX_SIZE));
1100 if (current < oldest) {
1101 current += GET_LEARN_MAX_WORD_COUNT(loctset->loct.handle);
1102 }
1103 is_first_search = 0;
1104 } else {
1105 loctset->loct.status = NJ_ST_SEARCH_END;
1106 return 0;
1107 }
1108
1109
1110 max_value = oldest;
1111
1112 p = ptr + (loctset->loct.top * NJ_INDEX_SIZE);
1113 eval = current;
1114 for (i = (NJ_UINT16)loctset->loct.top; i <= (NJ_UINT16)loctset->loct.bottom; i++) {
1115 que_id = GET_UINT16(p);
1116 if (que_id < oldest) {
1117 eval = que_id + GET_LEARN_MAX_WORD_COUNT(loctset->loct.handle);
1118 } else {
1119 eval = que_id;
1120 }
1121 #ifdef LEARN_DEBUG
1122 printf("que(%d) : eval = %d\n", que_id, eval);
1123 #endif
1124 is_better_freq = ((eval >= max_value) && ((is_first_search) || (eval < current))) ? 1 : 0;
1125
1126 if (is_better_freq) {
1127
1128 if (search_pattern == NJ_CUR_OP_LINK) {
1129
1130 ret = que_strcmp_complete_with_hyouki(iwnn, loctset->loct.handle, que_id,
1131 cond->yomi, cond->ylen, cond->kanji, 1);
1132 } else {
1133
1134 ret = str_que_cmp(iwnn, loctset->loct.handle, cond->yomi, cond->ylen, que_id, 2);
1135
1136 if (ret == 2) {
1137 ret = 0;
1138 }
1139 }
1140 if (ret < 0) {
1141 return ret;
1142 }
1143 if (ret >= 1) {
1144 if (search_pattern == NJ_CUR_OP_LINK) {
1145
1146
1147 num_count = continue_cnt(iwnn, loctset->loct.handle, que_id);
1148 if (num_count < 0) {
1149
1150 return num_count;
1151 }
1152
1153
1154 if (num_count >= ret) {
1155
1156 loctset->loct.current_info = (NJ_UINT8)(((num_count + 1) << 4) | ret);
1157 loctset->loct.current = i;
1158 max_value = eval;
1159 found = 1;
1160 }
1161 } else {
1162
1163
1164
1165
1166
1167 que = get_que_allHinsi(iwnn, loctset->loct.handle, que_id);
1168 if (njd_connect_test(cond, que->mae_hinsi, que->ato_hinsi)) {
1169
1170 loctset->loct.current_info = (NJ_UINT8)0x10;
1171 loctset->loct.current = i;
1172 max_value = eval;
1173 found = 1;
1174 #ifdef LEARN_DEBUG
1175 printf("---keep.");
1176 #endif
1177 }
1178 }
1179 }
1180 }
1181 p += NJ_INDEX_SIZE;
1182 }
1183
1184
1185 if (found == 0) {
1186 loctset->loct.status = NJ_ST_SEARCH_END;
1187 return 0;
1188 } else {
1189 loctset->loct.status = NJ_ST_SEARCH_READY;
1190 loctset->cache_freq = get_hindo(iwnn, loctset, search_pattern);
1191 return 1;
1192 }
1193
1194 }
1195
search_range_by_yomi(NJ_CLASS * iwnn,NJ_DIC_HANDLE handle,NJ_UINT8 op,NJ_CHAR * yomi,NJ_UINT16 len,NJ_UINT16 * from,NJ_UINT16 * to,NJ_UINT8 * forward_flag)1196 static NJ_INT16 search_range_by_yomi(NJ_CLASS *iwnn, NJ_DIC_HANDLE handle, NJ_UINT8 op,
1197 NJ_CHAR *yomi, NJ_UINT16 len, NJ_UINT16 *from, NJ_UINT16 *to,
1198 NJ_UINT8 *forward_flag) {
1199 NJ_UINT16 right, mid = 0, left, max;
1200 NJ_UINT16 que_id;
1201 NJ_UINT8 *ptr, *p;
1202 NJ_CHAR *str;
1203 NJ_INT16 ret = 0;
1204 NJ_INT32 found = 0;
1205 NJ_UINT8 slen;
1206 NJ_INT32 cmp;
1207
1208
1209
1210 ptr = get_search_index_address(handle, op);
1211
1212 max = GET_LEARN_WORD_COUNT(handle);
1213
1214 right = max - 1;
1215 left = 0;
1216
1217 #ifdef LEARN_DEBUG
1218 printf("src:[%s]\n", yomi);
1219 #endif
1220
1221 *forward_flag = 0;
1222
1223
1224 switch (op) {
1225 case NJ_CUR_OP_COMP:
1226 case NJ_CUR_OP_LINK:
1227 case NJ_CUR_OP_FORE:
1228
1229
1230
1231 break;
1232 default:
1233 return NJ_SET_ERR_VAL(NJ_FUNC_SEARCH_RANGE_BY_YOMI, NJ_ERR_PARAM_OPERATION);
1234 }
1235
1236 while (left <= right) {
1237 mid = left + ((right - left) / 2);
1238 p = ptr + (mid * NJ_INDEX_SIZE);
1239 que_id = GET_UINT16(p);
1240 str = get_string(iwnn, handle, que_id, &slen);
1241
1242 #ifdef IWNN_ERR_CHECK
1243 if (iwnn->err_check_flg == 3) {
1244 str = NULL;
1245 }
1246 #endif
1247 if (str == NULL) {
1248 return NJ_SET_ERR_VAL(NJ_FUNC_SEARCH_RANGE_BY_YOMI, NJ_ERR_DIC_BROKEN);
1249 }
1250
1251 ret = nj_strncmp(yomi, str, len);
1252 if (op != NJ_CUR_OP_FORE) {
1253
1254
1255 if (ret == 0) {
1256 if ((*forward_flag == 0) && (len <= (NJ_UINT16)slen)) {
1257
1258 *forward_flag = 1;
1259 }
1260 if (len > (NJ_UINT16)slen) {
1261 ret = 1;
1262 } else if (len < (NJ_UINT16)slen) {
1263 ret = -1;
1264 }
1265 }
1266 }
1267 #ifdef LEARN_DEBUG
1268 printf(" [%d][%d][%d]COMPARE:[%s] = %d\n", left, mid, right, str, ret);
1269 #endif
1270 if (ret == 0) {
1271
1272 found = 1;
1273 break;
1274 } else if (ret < 0) {
1275
1276 right = mid - 1;
1277 if (mid == 0) {
1278 break;
1279 }
1280 } else {
1281
1282 left = mid + 1;
1283 }
1284 }
1285
1286 if (!found) {
1287 return 0;
1288 }
1289
1290 if (mid == 0) {
1291 *from = mid;
1292 } else {
1293
1294 p = ((mid - 1) * NJ_INDEX_SIZE) + ptr;
1295
1296 for (cmp = mid - 1; cmp >= 0; cmp--) {
1297 que_id = GET_UINT16(p);
1298 str = get_string(iwnn, handle, que_id, &slen);
1299
1300 #ifdef IWNN_ERR_CHECK
1301 if (iwnn->err_check_flg == 4) {
1302 str = NULL;
1303 }
1304 #endif
1305 if (str == NULL) {
1306 return NJ_SET_ERR_VAL(NJ_FUNC_SEARCH_RANGE_BY_YOMI, NJ_ERR_DIC_BROKEN);
1307 }
1308
1309 if (op != NJ_CUR_OP_FORE) {
1310 ret = nj_strncmp(yomi, str, len);
1311 if (ret == 0) {
1312 if (len > (NJ_UINT16)slen) {
1313 ret = 1;
1314 } else if (len < (NJ_UINT16)slen) {
1315 ret = -1;
1316 }
1317 }
1318 if (ret > 0) {
1319
1320 break;
1321 }
1322 } else {
1323
1324 if (nj_strncmp(yomi, str, len) != 0) {
1325 break;
1326 }
1327 }
1328 p -= NJ_INDEX_SIZE;
1329 }
1330 if (cmp < 0) {
1331 *from = 0;
1332 } else {
1333 *from = (NJ_UINT16)cmp + 1;
1334 }
1335 }
1336
1337 #ifdef LEARN_DEBUG
1338 printf(" >> from:(%d)\n", *from);
1339 #endif
1340
1341 #ifdef IWNN_ERR_CHECK
1342 if (iwnn->err_check_flg == 5) {
1343 mid = max - 2;
1344 }
1345 #endif
1346 if ((mid + 1) >= max) {
1347 *to = mid;
1348 } else {
1349
1350 p = ((mid + 1) * NJ_INDEX_SIZE) + ptr;
1351
1352 for (right = mid + 1; right < max; right++) {
1353 que_id = GET_UINT16(p);
1354 str = get_string(iwnn, handle, que_id, &slen);
1355
1356 #ifdef IWNN_ERR_CHECK
1357 if (iwnn->err_check_flg == 5) {
1358 str = NULL;
1359 }
1360 #endif
1361 if (str == NULL) {
1362 return NJ_SET_ERR_VAL(NJ_FUNC_SEARCH_RANGE_BY_YOMI, NJ_ERR_DIC_BROKEN);
1363 }
1364
1365 if (op != NJ_CUR_OP_FORE) {
1366 ret = nj_strncmp(yomi, str, len);
1367 if (ret == 0) {
1368 if (len > (NJ_UINT16)slen) {
1369 ret = 1;
1370 } else if (len < (NJ_UINT16)slen) {
1371 ret = -1;
1372 }
1373 }
1374 if (ret < 0) {
1375
1376 break;
1377 }
1378 } else {
1379
1380 if (nj_strncmp(yomi, str, len) != 0) {
1381 break;
1382 }
1383 }
1384 p += NJ_INDEX_SIZE;
1385 }
1386 *to = right - 1;
1387 }
1388
1389 #ifdef LEARN_DEBUG
1390 printf(" >> to:(%d)\n", *to);
1391 #endif
1392 return 1;
1393 }
1394
search_range_by_yomi_multi(NJ_CLASS * iwnn,NJ_DIC_HANDLE handle,NJ_CHAR * yomi,NJ_UINT16 len,NJ_UINT16 * from,NJ_UINT16 * to)1395 static NJ_INT16 search_range_by_yomi_multi(NJ_CLASS *iwnn, NJ_DIC_HANDLE handle,
1396 NJ_CHAR *yomi, NJ_UINT16 len, NJ_UINT16 *from, NJ_UINT16 *to) {
1397 NJ_UINT16 right, mid = 0, left, max = 0;
1398 NJ_UINT16 que_id;
1399 NJ_UINT8 *ptr, *p;
1400 NJ_INT16 ret = 0;
1401 NJ_UINT16 comp_len;
1402 NJ_UINT16 i, char_len;
1403 NJ_INT32 found = 0;
1404 NJ_INT32 cmp;
1405 NJ_CHAR comp_yomi[NJ_MAX_LEN + NJ_TERM_LEN];
1406 NJ_CHAR *pYomi;
1407
1408
1409
1410
1411 ptr = LEARN_INDEX_TOP_ADDR(handle);
1412
1413
1414 max = GET_LEARN_WORD_COUNT(handle);
1415
1416 #ifdef LEARN_DEBUG
1417 printf("src:[%s]\n", yomi);
1418 #endif
1419
1420 comp_len = 0;
1421 pYomi = &yomi[0];
1422 while (comp_len < len) {
1423
1424
1425 char_len = NJ_CHAR_LEN(pYomi);
1426 for (i = 0; i < char_len; i++) {
1427 *(comp_yomi + comp_len) = *pYomi;
1428 comp_len++;
1429 pYomi++;
1430 }
1431 *(comp_yomi + comp_len) = NJ_CHAR_NUL;
1432
1433 right = max - 1;
1434 left = 0;
1435 while (left <= right) {
1436 mid = left + ((right - left) / 2);
1437 p = ptr + (mid * NJ_INDEX_SIZE);
1438 que_id = GET_UINT16(p);
1439
1440
1441 ret = str_que_cmp(iwnn, handle, comp_yomi, comp_len, que_id, 1);
1442 if (ret < 0) {
1443 return NJ_SET_ERR_VAL(NJ_FUNC_SEARCH_RANGE_BY_YOMI_MULTI, NJ_ERR_DIC_BROKEN);
1444 }
1445
1446 #ifdef LEARN_DEBUG
1447 printf(" [%d][%d][%d]COMPARE:[%s] = %d\n", left, mid, right, str, ret);
1448 #endif
1449 if (ret == 1) {
1450
1451 found = 1;
1452 break;
1453 } else if (ret == 0) {
1454
1455 right = mid - 1;
1456 if (mid == 0) {
1457 break;
1458 }
1459 } else {
1460
1461 left = mid + 1;
1462 }
1463 }
1464
1465 if (found) {
1466 break;
1467 }
1468 }
1469
1470 if (!found) {
1471
1472 return 0;
1473 }
1474
1475
1476 if (mid == 0) {
1477 *from = mid;
1478 } else {
1479
1480 p = ((mid - 1) * NJ_INDEX_SIZE) + ptr;
1481
1482 for (cmp = mid - 1; cmp >= 0; cmp--) {
1483 que_id = GET_UINT16(p);
1484 ret = str_que_cmp(iwnn, handle, comp_yomi, comp_len, que_id, 1);
1485 if (ret < 0) {
1486 return NJ_SET_ERR_VAL(NJ_FUNC_SEARCH_RANGE_BY_YOMI_MULTI, NJ_ERR_DIC_BROKEN);
1487 }
1488 if (ret == 2) {
1489 break;
1490 }
1491 p -= NJ_INDEX_SIZE;
1492 }
1493 if (cmp < 0) {
1494 *from = 0;
1495 } else {
1496 *from = (NJ_UINT16)cmp + 1;
1497 }
1498 }
1499
1500 #ifdef LEARN_DEBUG
1501 printf(" >> from:(%d)\n", *from);
1502 #endif
1503
1504
1505 if ((mid + 1) >= max) {
1506 *to = mid;
1507 } else {
1508
1509 p = ((mid + 1) * NJ_INDEX_SIZE) + ptr;
1510
1511 for (right = mid + 1; right < max; right++) {
1512 que_id = GET_UINT16(p);
1513 ret = str_que_cmp(iwnn, handle, yomi, len, que_id, 1);
1514 if (ret < 0) {
1515 return NJ_SET_ERR_VAL(NJ_FUNC_SEARCH_RANGE_BY_YOMI_MULTI, NJ_ERR_DIC_BROKEN);
1516 }
1517 if (ret == 0) {
1518 break;
1519 }
1520 p += NJ_INDEX_SIZE;
1521 }
1522 *to = right - 1;
1523 }
1524
1525 #ifdef LEARN_DEBUG
1526 printf(" >> to:(%d)\n", *to);
1527 #endif
1528 return 1;
1529 }
1530
str_que_cmp(NJ_CLASS * iwnn,NJ_DIC_HANDLE handle,NJ_CHAR * yomi,NJ_UINT16 yomiLen,NJ_UINT16 que_id,NJ_UINT8 mode)1531 static NJ_INT16 str_que_cmp(NJ_CLASS *iwnn, NJ_DIC_HANDLE handle, NJ_CHAR *yomi,
1532 NJ_UINT16 yomiLen, NJ_UINT16 que_id, NJ_UINT8 mode) {
1533 NJ_UINT8 *queYomi;
1534 NJ_UINT8 *yomiPtr;
1535 NJ_UINT16 yomiByte;
1536 NJ_UINT16 yomiPos;
1537 NJ_UINT8 queYomiByte, queKouhoByte;
1538 NJ_UINT8 queYomiPos, queYomiSearchArea;
1539 NJ_INT16 complete;
1540 NJ_UINT8 *top_addr;
1541 NJ_UINT8 *bottom_addr;
1542 NJ_UINT16 que_size;
1543
1544
1545 #ifdef IWNN_ERR_CHECK
1546 if (iwnn->err_check_flg == 6) {
1547 que_id = GET_LEARN_MAX_WORD_COUNT(handle);
1548 }
1549 #endif
1550 if (que_id >= GET_LEARN_MAX_WORD_COUNT(handle)) {
1551
1552 return NJ_SET_ERR_VAL(NJ_FUNC_STR_QUE_CMP, NJ_ERR_DIC_BROKEN);
1553 }
1554
1555 queYomi = POS_TO_ADDRESS(handle, que_id);
1556 #ifdef IWNN_ERR_CHECK
1557 if (iwnn->err_check_flg == 7) {
1558 *queYomi = 0x03;
1559 }
1560 #endif
1561 switch (GET_TYPE_FROM_DATA(queYomi)) {
1562 case QUE_TYPE_EMPTY:
1563 case QUE_TYPE_JIRI:
1564 case QUE_TYPE_FZK:
1565 break;
1566 default:
1567
1568 return NJ_SET_ERR_VAL(NJ_FUNC_STR_QUE_CMP, NJ_ERR_DIC_BROKEN);
1569 }
1570
1571
1572 if ((mode == 2) && (yomiLen == 0)) {
1573 return 1;
1574 }
1575
1576
1577 queYomiByte = GET_YSIZE_FROM_DATA(queYomi);
1578 queKouhoByte= GET_KSIZE_FROM_DATA(queYomi);
1579
1580 top_addr = LEARN_DATA_TOP_ADDR(handle);
1581 que_size = QUE_SIZE(handle);
1582
1583
1584 queYomi += LEARN_QUE_STRING_OFFSET;
1585 queYomiSearchArea = (NJ_UINT8)(QUE_SIZE(handle) - LEARN_QUE_STRING_OFFSET);
1586
1587 complete = 0;
1588 yomiPos = 0; queYomiPos = 0;
1589 yomiPtr = (NJ_UINT8*)yomi;
1590 yomiByte = yomiLen * sizeof(NJ_CHAR);
1591
1592
1593 while ((complete = (*yomiPtr - *queYomi)) == 0) {
1594 yomiPos++; queYomiPos++;
1595
1596 if (queYomiPos >= queYomiByte) {
1597 if (queYomiByte == yomiByte) {
1598
1599 return 1;
1600 } else if (mode == 2) {
1601
1602 return 2;
1603 } else {
1604
1605 return (mode + 1);
1606 }
1607 }
1608 if (yomiPos >= yomiByte) {
1609
1610 break;
1611 } else {
1612 yomiPtr++; queYomi++;
1613 #ifdef IWNN_ERR_CHECK
1614 if (iwnn->err_check_flg == 8) {
1615 queYomiPos = queYomiSearchArea;
1616 }
1617 #endif
1618 if (queYomiPos >= queYomiSearchArea) {
1619
1620 bottom_addr = top_addr;
1621 bottom_addr += que_size * GET_LEARN_MAX_WORD_COUNT(handle) - 1;
1622 if (queYomi >= bottom_addr) {
1623 queYomi = top_addr;
1624 }
1625
1626
1627 if (*queYomi++ != QUE_TYPE_NEXT) {
1628
1629 return NJ_SET_ERR_VAL(NJ_FUNC_STR_QUE_CMP, NJ_ERR_DIC_BROKEN);
1630 }
1631 queYomiSearchArea += (NJ_UINT8)(que_size - 1);
1632 }
1633 }
1634 }
1635 if (complete == 0) {
1636 if (yomiByte < queYomiByte) {
1637
1638 if (mode == 2) {
1639 return 1;
1640 }
1641
1642 return 0;
1643 } else {
1644
1645 return 2;
1646 }
1647 } else if (complete < 0) {
1648
1649 return 0;
1650 } else {
1651
1652 return 2;
1653 }
1654 }
1655
calculate_hindo(NJ_DIC_HANDLE handle,NJ_INT32 freq,NJ_DIC_FREQ * dic_freq,NJ_INT16 freq_max,NJ_INT16 freq_min)1656 static NJ_HINDO calculate_hindo(NJ_DIC_HANDLE handle, NJ_INT32 freq, NJ_DIC_FREQ *dic_freq, NJ_INT16 freq_max, NJ_INT16 freq_min) {
1657 NJ_UINT16 max;
1658 NJ_HINDO hindo;
1659
1660
1661 max = GET_LEARN_MAX_WORD_COUNT(handle);
1662
1663
1664
1665
1666 if (NJ_GET_DIC_TYPE(handle) == NJ_DIC_TYPE_USER) {
1667
1668 hindo = (NJ_INT16)dic_freq->base;
1669 } else {
1670
1671 if (max > 1) {
1672
1673 hindo = CALCULATE_HINDO(freq, dic_freq->base, dic_freq->high, (max-1));
1674 } else {
1675
1676 hindo = (NJ_INT16)dic_freq->high;
1677 }
1678 }
1679 return NORMALIZE_HINDO(hindo, freq_max, freq_min);
1680 }
1681
get_hindo(NJ_CLASS * iwnn,NJ_SEARCH_LOCATION_SET * loctset,NJ_UINT8 search_pattern)1682 static NJ_HINDO get_hindo(NJ_CLASS *iwnn, NJ_SEARCH_LOCATION_SET *loctset,
1683 NJ_UINT8 search_pattern) {
1684 NJ_WQUE *que;
1685 NJ_UINT16 que_id, oldest;
1686 NJ_UINT8 offset;
1687 NJ_INT32 dic_freq;
1688 NJ_UINT16 max;
1689 NJ_UINT8 *learn_index_top_addr;
1690
1691
1692
1693 learn_index_top_addr = get_search_index_address(loctset->loct.handle, search_pattern);
1694
1695 que_id = (NJ_UINT16)GET_UINT16(learn_index_top_addr +
1696 ((loctset->loct.current & 0xffffU) * NJ_INDEX_SIZE));
1697 oldest = GET_LEARN_NEXT_WORD_POS(loctset->loct.handle);
1698
1699 offset = (loctset->loct.current_info & 0x0f);
1700 while (offset--) {
1701 que_id = search_next_que(loctset->loct.handle, que_id);
1702 }
1703
1704 que = get_que(iwnn, loctset->loct.handle, que_id);
1705 if (que == NULL) {
1706 return INIT_HINDO;
1707 }
1708
1709 max = GET_LEARN_MAX_WORD_COUNT(loctset->loct.handle);
1710 if (que_id >= oldest) {
1711 dic_freq = que_id - oldest;
1712 } else {
1713 dic_freq = que_id - oldest + max;
1714 }
1715
1716
1717 return calculate_hindo(loctset->loct.handle, dic_freq, &(loctset->dic_freq), 1000, 0);
1718 }
1719
njd_l_get_word(NJ_CLASS * iwnn,NJ_SEARCH_LOCATION_SET * loctset,NJ_WORD * word)1720 NJ_INT16 njd_l_get_word(NJ_CLASS *iwnn, NJ_SEARCH_LOCATION_SET *loctset, NJ_WORD *word) {
1721 NJ_WQUE *que;
1722 NJ_UINT16 que_id;
1723 NJ_UINT8 offset;
1724 NJ_UINT8 *learn_index_top_addr;
1725
1726
1727
1728 learn_index_top_addr = get_search_index_address(loctset->loct.handle, GET_LOCATION_OPERATION(loctset->loct.status));
1729
1730 que_id = (NJ_UINT16)GET_UINT16(learn_index_top_addr +
1731 ((loctset->loct.current & 0xffff) * NJ_INDEX_SIZE));
1732
1733 offset = (loctset->loct.current_info & 0x0f);
1734 while (offset--) {
1735 que_id = search_next_que(loctset->loct.handle, que_id);
1736 }
1737
1738 que = get_que(iwnn, loctset->loct.handle, que_id);
1739 if (que == NULL) {
1740 return NJ_SET_ERR_VAL(NJ_FUNC_NJD_L_GET_WORD, NJ_ERR_CANNOT_GET_QUE);
1741 }
1742
1743 word->stem.loc = loctset->loct;
1744
1745 word->stem.loc.current &= 0x0000ffff;
1746 word->stem.loc.current |= ((NJ_UINT32)que_id << 16);
1747
1748
1749 word->stem.hindo = loctset->cache_freq;
1750
1751 NJ_SET_FPOS_TO_STEM(word, que->mae_hinsi);
1752 NJ_SET_YLEN_TO_STEM(word, que->yomi_len);
1753 if (que->hyouki_len > 0) {
1754 NJ_SET_KLEN_TO_STEM(word, que->hyouki_len);
1755 } else {
1756
1757 NJ_SET_KLEN_TO_STEM(word, que->yomi_len);
1758 }
1759 NJ_SET_BPOS_TO_STEM(word, que->ato_hinsi);
1760
1761
1762 word->stem.type = 0;
1763
1764 return 1;
1765 }
1766
njd_l_get_stroke(NJ_CLASS * iwnn,NJ_WORD * word,NJ_CHAR * stroke,NJ_UINT16 size)1767 NJ_INT16 njd_l_get_stroke(NJ_CLASS *iwnn, NJ_WORD *word, NJ_CHAR *stroke, NJ_UINT16 size) {
1768 NJ_UINT16 que_id;
1769 NJ_CHAR *str;
1770 NJ_UINT8 slen;
1771 NJ_UINT8 ylen;
1772
1773
1774 que_id = (NJ_UINT16)(word->stem.loc.current >> 16);
1775
1776
1777 ylen = (NJ_UINT8)NJ_GET_YLEN_FROM_STEM(word);
1778
1779 if ((NJ_UINT16)((ylen+ NJ_TERM_LEN)*sizeof(NJ_CHAR)) > size) {
1780
1781 return NJ_SET_ERR_VAL(NJ_FUNC_NJD_L_GET_STROKE, NJ_ERR_BUFFER_NOT_ENOUGH);
1782 }
1783 if (ylen == 0) {
1784 return NJ_SET_ERR_VAL(NJ_FUNC_NJD_L_GET_STROKE, NJ_ERR_INVALID_RESULT);
1785 }
1786 str = get_string(iwnn, word->stem.loc.handle, que_id, &slen);
1787
1788 #ifdef IWNN_ERR_CHECK
1789 if (iwnn->err_check_flg == 9) {
1790 str = NULL;
1791 }
1792 #endif
1793
1794 if (str == NULL) {
1795 return NJ_SET_ERR_VAL(NJ_FUNC_NJD_L_GET_STROKE, NJ_ERR_DIC_BROKEN);
1796 }
1797
1798
1799 nj_strcpy(stroke, str);
1800
1801 return slen;
1802 }
1803
njd_l_get_candidate(NJ_CLASS * iwnn,NJ_WORD * word,NJ_CHAR * candidate,NJ_UINT16 size)1804 NJ_INT16 njd_l_get_candidate(NJ_CLASS *iwnn, NJ_WORD *word,
1805 NJ_CHAR *candidate, NJ_UINT16 size) {
1806 NJ_UINT16 que_id;
1807 NJ_CHAR *str;
1808 NJ_UINT16 klen;
1809 NJ_UINT8 slen;
1810
1811
1812 que_id = (NJ_UINT16)(word->stem.loc.current >> 16);
1813
1814
1815 klen = NJ_GET_KLEN_FROM_STEM(word);
1816
1817 if (size < ((klen+NJ_TERM_LEN)*sizeof(NJ_CHAR))) {
1818
1819 return NJ_SET_ERR_VAL(NJ_FUNC_NJD_L_GET_CANDIDATE, NJ_ERR_BUFFER_NOT_ENOUGH);
1820 }
1821 str = get_hyouki(iwnn, word->stem.loc.handle, que_id, &slen);
1822 #ifdef IWNN_ERR_CHECK
1823 if (iwnn->err_check_flg == 10) {
1824 str = NULL;
1825 }
1826 #endif
1827 if (str == NULL) {
1828
1829 return NJ_SET_ERR_VAL(NJ_FUNC_NJD_L_GET_CANDIDATE, NJ_ERR_DIC_BROKEN);
1830 }
1831
1832
1833 nj_strcpy(candidate, str);
1834
1835 return klen;
1836 }
1837
njd_l_check_dic(NJ_CLASS * iwnn,NJ_DIC_HANDLE handle)1838 NJ_INT16 njd_l_check_dic(NJ_CLASS *iwnn, NJ_DIC_HANDLE handle) {
1839 NJ_UINT16 flg;
1840 NJ_UINT16 word_cnt, max;
1841 NJ_UINT8 *ptr;
1842 NJ_UINT16 target_id;
1843 NJ_UINT16 i;
1844 NJ_UINT16 id1 = 0;
1845 NJ_UINT8 slen;
1846
1847
1848
1849 if ((NJ_GET_DIC_TYPE(handle) != NJ_DIC_TYPE_USER)) {
1850
1851 return NJ_SET_ERR_VAL(NJ_FUNC_NJD_L_CHECK_DIC, NJ_ERR_DIC_TYPE_INVALID);
1852 }
1853
1854
1855 word_cnt = GET_LEARN_WORD_COUNT(handle);
1856 max = GET_LEARN_MAX_WORD_COUNT(handle);
1857 if (word_cnt > max) {
1858
1859 return NJ_SET_ERR_VAL(NJ_FUNC_NJD_L_CHECK_DIC,
1860 NJ_ERR_DIC_BROKEN);
1861 }
1862
1863 ptr = LEARN_INDEX_TOP_ADDR(handle);
1864 for (i = 0; i < word_cnt; i++) {
1865 id1 = GET_UINT16(ptr);
1866
1867 if (id1 >= max) {
1868 return NJ_SET_ERR_VAL(NJ_FUNC_NJD_L_CHECK_DIC,
1869 NJ_ERR_DIC_BROKEN);
1870 }
1871 ptr += NJ_INDEX_SIZE;
1872 }
1873
1874
1875 ptr = LEARN_INDEX_TOP_ADDR2(handle);
1876 for (i = 0; i < word_cnt; i++) {
1877 id1 = GET_UINT16(ptr);
1878
1879 if (id1 >= max) {
1880 return NJ_SET_ERR_VAL(NJ_FUNC_NJD_L_CHECK_DIC,
1881 NJ_ERR_DIC_BROKEN);
1882 }
1883 ptr += NJ_INDEX_SIZE;
1884 }
1885
1886
1887 flg = GET_UINT16(handle + POS_WRITE_FLG);
1888
1889 target_id = GET_UINT16(handle + POS_WRITE_FLG + 2);
1890
1891
1892
1893 if (((flg != word_cnt) && (flg != (word_cnt + 1)) && (flg != (word_cnt - 1))) ||
1894 (target_id >= max)) {
1895 return NJ_SET_ERR_VAL(NJ_FUNC_NJD_L_CHECK_DIC,
1896 NJ_ERR_DIC_BROKEN);
1897 }
1898
1899
1900 if (flg == (word_cnt + 1)) {
1901 return NJ_SET_ERR_VAL(NJ_FUNC_NJD_L_CHECK_DIC, NJ_ERR_DIC_BROKEN);
1902 } else if (flg == (word_cnt - 1)) {
1903 return NJ_SET_ERR_VAL(NJ_FUNC_NJD_L_CHECK_DIC, NJ_ERR_DIC_BROKEN);
1904 }
1905
1906 word_cnt = GET_LEARN_WORD_COUNT(handle);
1907
1908 ptr = LEARN_INDEX_TOP_ADDR(handle);
1909 for (i = 0; i < word_cnt; i++) {
1910 id1 = GET_UINT16(ptr);
1911 if (get_hyouki(iwnn, handle, id1, &slen) == NULL) {
1912 return NJ_SET_ERR_VAL(NJ_FUNC_NJD_L_CHECK_DIC,
1913 NJ_ERR_DIC_BROKEN);
1914 }
1915 ptr += NJ_INDEX_SIZE;
1916 }
1917
1918 ptr = LEARN_INDEX_TOP_ADDR2(handle);
1919 for (i = 0; i < word_cnt; i++) {
1920 id1 = GET_UINT16(ptr);
1921
1922 if (id1 >= max) {
1923 return NJ_SET_ERR_VAL(NJ_FUNC_NJD_L_CHECK_DIC,
1924 NJ_ERR_DIC_BROKEN);
1925 }
1926 ptr += NJ_INDEX_SIZE;
1927 }
1928
1929 return 0;
1930 }
1931
get_cand_by_evaluate2(NJ_CLASS * iwnn,NJ_SEARCH_CONDITION * cond,NJ_SEARCH_LOCATION_SET * loctset,NJ_UINT8 search_pattern,NJ_UINT16 idx)1932 static NJ_INT16 get_cand_by_evaluate2(NJ_CLASS *iwnn, NJ_SEARCH_CONDITION *cond,
1933 NJ_SEARCH_LOCATION_SET *loctset,
1934 NJ_UINT8 search_pattern,
1935 NJ_UINT16 idx) {
1936 NJ_UINT16 from, to, i;
1937 NJ_UINT16 que_id, oldest;
1938 NJ_UINT32 max_value, eval, current;
1939 NJ_UINT8 *ptr, *p;
1940 NJ_WQUE *que;
1941 NJ_INT16 ret = 0;
1942 NJ_INT32 found = 0;
1943 NJ_UINT8 forward_flag = 0;
1944
1945
1946 NJ_UINT16 abIdx;
1947 NJ_UINT16 abIdx_old;
1948 NJ_UINT16 tmp_len;
1949 NJ_UINT16 yomi_clen;
1950 NJ_UINT16 j,l,m;
1951 NJ_UINT8 cmpflg;
1952 NJ_UINT8 endflg = 0;
1953 NJ_CHAR *str;
1954 NJ_CHAR *key;
1955 NJ_CHAR char_tmp[NJ_MAX_LEN + NJ_TERM_LEN];
1956 NJ_CHAR *pchar_tmp;
1957 NJ_SEARCH_CACHE *psrhCache = cond->ds->dic[idx].srhCache;
1958 NJ_UINT16 endIdx;
1959 NJ_UINT8 slen;
1960 NJ_UINT16 addcnt = 0;
1961 NJ_CHAR *yomi;
1962 NJ_UINT8 aimai_flg = 0x01;
1963 NJ_CHARSET *pCharset = cond->charset;
1964
1965
1966 if (NJ_GET_CACHEOVER_FROM_SCACHE(psrhCache)) {
1967 aimai_flg = 0x00;
1968 }
1969
1970
1971 ptr = get_search_index_address(loctset->loct.handle, cond->operation);
1972
1973
1974 oldest = GET_LEARN_NEXT_WORD_POS(loctset->loct.handle);
1975 max_value = oldest;
1976
1977
1978 current = 0;
1979 if (GET_LOCATION_STATUS(loctset->loct.status) == NJ_ST_SEARCH_NO_INIT) {
1980
1981
1982 key = cond->ds->keyword;
1983 yomi = cond->yomi;
1984 yomi_clen = cond->yclen;
1985
1986
1987 endflg = 0x00;
1988
1989 if (psrhCache->keyPtr[0] == 0xFFFF) {
1990 cmpflg = 0x01;
1991 psrhCache->keyPtr[0] = 0x0000;
1992 } else {
1993 cmpflg = 0x00;
1994 }
1995
1996 for (i = 0; i < yomi_clen; i++) {
1997 j = i;
1998
1999
2000 if (!cmpflg) {
2001
2002 if (((j != 0) && (psrhCache->keyPtr[j] == 0)) || (psrhCache->keyPtr[j+1] == 0)) {
2003
2004 cmpflg = 0x01;
2005 } else {
2006
2007 }
2008 }
2009
2010 if (cmpflg) {
2011
2012 if (!j) {
2013
2014 abIdx = 0;
2015 addcnt = 0;
2016 nj_charncpy(char_tmp, yomi, 1);
2017 tmp_len = nj_strlen(char_tmp);
2018 ret = search_range_by_yomi(iwnn, loctset->loct.handle, search_pattern,
2019 char_tmp, tmp_len, &from,
2020 &to, &forward_flag);
2021 if (ret < 0) {
2022
2023
2024 psrhCache->keyPtr[j+1] = abIdx;
2025 loctset->loct.status = NJ_ST_SEARCH_END;
2026 return ret;
2027 } else if (ret > 0) {
2028
2029 psrhCache->storebuff[abIdx].top = from;
2030 psrhCache->storebuff[abIdx].bottom = to;
2031 psrhCache->storebuff[abIdx].idx_no = (NJ_INT8)tmp_len;
2032 addcnt++;
2033 abIdx++;
2034 psrhCache->keyPtr[j+1] = abIdx;
2035 } else {
2036 psrhCache->keyPtr[j+1] = abIdx;
2037 }
2038
2039 if ((!endflg) && (pCharset != NULL) && aimai_flg) {
2040
2041 for (l = 0; l < pCharset->charset_count; l++) {
2042
2043 if (nj_charncmp(yomi, pCharset->from[l], 1) == 0) {
2044
2045 nj_strcpy(char_tmp, pCharset->to[l]);
2046 tmp_len = nj_strlen(char_tmp);
2047 ret = search_range_by_yomi(iwnn, loctset->loct.handle, search_pattern,
2048 char_tmp, tmp_len, &from, &to, &forward_flag);
2049 if (ret < 0) {
2050
2051
2052 psrhCache->keyPtr[j+1] = abIdx;
2053 loctset->loct.status = NJ_ST_SEARCH_END;
2054 return ret;
2055 } else if (ret > 0) {
2056
2057
2058 if (abIdx >= NJ_SEARCH_CACHE_SIZE) {
2059 psrhCache->keyPtr[j+1] = 0;
2060 return NJ_SET_ERR_VAL(NJ_FUNC_SEARCH_RANGE_BY_YOMI, NJ_ERR_CACHE_NOT_ENOUGH);
2061 }
2062 psrhCache->storebuff[abIdx].top = from;
2063 psrhCache->storebuff[abIdx].bottom = to;
2064 psrhCache->storebuff[abIdx].idx_no = (NJ_INT8)tmp_len;
2065 if (addcnt == 0) {
2066 psrhCache->keyPtr[j] = abIdx;
2067 }
2068 abIdx++;
2069 addcnt++;
2070 psrhCache->keyPtr[j+1] = abIdx;
2071 } else {
2072 psrhCache->keyPtr[j+1] = abIdx;
2073 }
2074 }
2075 }
2076 }
2077 } else {
2078
2079 if (psrhCache->keyPtr[j] == psrhCache->keyPtr[j-1]) {
2080
2081 psrhCache->keyPtr[j+1] = psrhCache->keyPtr[j-1];
2082 endflg = 0x01;
2083 } else {
2084
2085 endIdx = psrhCache->keyPtr[j];
2086 abIdx_old = psrhCache->keyPtr[j-1];
2087
2088 if (NJ_GET_CACHEOVER_FROM_SCACHE(psrhCache)) {
2089 abIdx = psrhCache->keyPtr[j - 1];
2090 psrhCache->keyPtr[j] = abIdx;
2091 } else {
2092 abIdx = psrhCache->keyPtr[j];
2093 }
2094 addcnt = 0;
2095
2096 if ((abIdx > NJ_SEARCH_CACHE_SIZE) || (abIdx_old >= NJ_SEARCH_CACHE_SIZE) ||
2097 (endIdx > NJ_SEARCH_CACHE_SIZE)) {
2098
2099 return NJ_SET_ERR_VAL(NJ_FUNC_SEARCH_RANGE_BY_YOMI, NJ_ERR_CACHE_BROKEN);
2100 }
2101 for (m = abIdx_old; m < endIdx; m++) {
2102
2103 p = ptr + (psrhCache->storebuff[m].top * NJ_INDEX_SIZE);
2104 que_id = GET_UINT16(p);
2105
2106
2107 str = get_string(iwnn, loctset->loct.handle, que_id, &slen);
2108
2109 if (str == NULL) {
2110 return NJ_SET_ERR_VAL(NJ_FUNC_SEARCH_RANGE_BY_YOMI, NJ_ERR_DIC_BROKEN);
2111 }
2112
2113
2114 nj_strncpy(char_tmp, str, psrhCache->storebuff[m].idx_no);
2115 char_tmp[psrhCache->storebuff[m].idx_no] = NJ_CHAR_NUL;
2116
2117 pchar_tmp = &char_tmp[psrhCache->storebuff[m].idx_no];
2118 nj_charncpy(pchar_tmp, yomi, 1);
2119 tmp_len = nj_strlen(char_tmp);
2120
2121
2122 ret = search_range_by_yomi2(iwnn, loctset->loct.handle, search_pattern,
2123 char_tmp, tmp_len,
2124 (NJ_UINT16)(psrhCache->storebuff[m].top),
2125 (NJ_UINT16)(psrhCache->storebuff[m].bottom),
2126 &from, &to, &forward_flag);
2127 if (ret < 0) {
2128
2129
2130 psrhCache->keyPtr[j+1] = abIdx;
2131 loctset->loct.status = NJ_ST_SEARCH_END;
2132 return ret;
2133 } else if (ret > 0) {
2134
2135
2136 if (abIdx >= NJ_SEARCH_CACHE_SIZE) {
2137 psrhCache->keyPtr[j+1] = 0;
2138 return NJ_SET_ERR_VAL(NJ_FUNC_SEARCH_RANGE_BY_YOMI, NJ_ERR_CACHE_NOT_ENOUGH);
2139 }
2140 psrhCache->storebuff[abIdx].top = from;
2141 psrhCache->storebuff[abIdx].bottom = to;
2142 psrhCache->storebuff[abIdx].idx_no = (NJ_INT8)tmp_len;
2143 if (addcnt == 0) {
2144 psrhCache->keyPtr[j] = abIdx;
2145 }
2146 abIdx++;
2147 addcnt++;
2148 psrhCache->keyPtr[j+1] = abIdx;
2149 } else {
2150 psrhCache->keyPtr[j+1] = abIdx;
2151 }
2152
2153 if ((!endflg) && (pCharset != NULL) && aimai_flg) {
2154
2155 for (l = 0; l < pCharset->charset_count; l++) {
2156
2157 if (nj_charncmp(yomi, pCharset->from[l], 1) == 0) {
2158
2159 tmp_len = nj_strlen(pCharset->to[l]);
2160
2161 nj_strncpy(pchar_tmp, pCharset->to[l], tmp_len);
2162 *(pchar_tmp + tmp_len) = NJ_CHAR_NUL;
2163 tmp_len = nj_strlen(char_tmp);
2164 ret = search_range_by_yomi2(iwnn, loctset->loct.handle, search_pattern,
2165 char_tmp, tmp_len,
2166 (NJ_UINT16)(psrhCache->storebuff[m].top),
2167 (NJ_UINT16)(psrhCache->storebuff[m].bottom),
2168 &from, &to, &forward_flag);
2169 if (ret < 0) {
2170
2171
2172 psrhCache->keyPtr[j+1] = abIdx;
2173 loctset->loct.status = NJ_ST_SEARCH_END;
2174 return ret;
2175 } else if (ret > 0) {
2176
2177
2178 if (abIdx >= NJ_SEARCH_CACHE_SIZE) {
2179 psrhCache->keyPtr[j+1] = 0;
2180 return NJ_SET_ERR_VAL(NJ_FUNC_SEARCH_RANGE_BY_YOMI, NJ_ERR_CACHE_NOT_ENOUGH);
2181 }
2182 psrhCache->storebuff[abIdx].top = from;
2183 psrhCache->storebuff[abIdx].bottom = to;
2184 psrhCache->storebuff[abIdx].idx_no = (NJ_INT8)tmp_len;
2185 abIdx++;
2186 addcnt++;
2187 psrhCache->keyPtr[j+1] = abIdx;
2188 } else {
2189 psrhCache->keyPtr[j+1] = abIdx;
2190 }
2191 }
2192 }
2193 }
2194 }
2195 }
2196 }
2197 }
2198 yomi += UTL_CHAR(yomi);
2199 key += UTL_CHAR(key);
2200 }
2201
2202
2203 if ((addcnt == 0) && (psrhCache->keyPtr[yomi_clen - 1] == psrhCache->keyPtr[yomi_clen])) {
2204 endflg = 0x01;
2205 }
2206
2207 if (endflg) {
2208 loctset->loct.status = NJ_ST_SEARCH_END;
2209 return 0;
2210 }
2211 } else if (GET_LOCATION_STATUS(loctset->loct.status) == NJ_ST_SEARCH_READY) {
2212 current = GET_UINT16(ptr + (loctset->loct.current * NJ_INDEX_SIZE));
2213 if (current < oldest) {
2214 current += GET_LEARN_MAX_WORD_COUNT(loctset->loct.handle);
2215 }
2216 } else {
2217 loctset->loct.status = NJ_ST_SEARCH_END;
2218 return 0;
2219 }
2220
2221
2222 j = cond->yclen - 1;
2223
2224 abIdx = psrhCache->keyPtr[j];
2225 abIdx_old = psrhCache->keyPtr[j+1];
2226
2227 endIdx = abIdx_old;
2228 if ((abIdx >= NJ_SEARCH_CACHE_SIZE) || (abIdx_old > NJ_SEARCH_CACHE_SIZE)) {
2229
2230 return NJ_SET_ERR_VAL(NJ_FUNC_SEARCH_RANGE_BY_YOMI, NJ_ERR_CACHE_BROKEN);
2231 }
2232 p = ptr + (psrhCache->storebuff[abIdx].top * NJ_INDEX_SIZE);
2233 que_id = GET_UINT16(p);
2234 eval = current;
2235
2236
2237
2238 if (psrhCache->keyPtr[j] < psrhCache->keyPtr[j + 1]) {
2239 if (GET_LOCATION_STATUS(loctset->loct.status) == NJ_ST_SEARCH_NO_INIT) {
2240 endIdx = abIdx + 1;
2241 NJ_SET_AIMAI_TO_SCACHE(psrhCache);
2242 }
2243
2244 for (m = abIdx; m < endIdx; m++) {
2245 p = ptr + (psrhCache->storebuff[m].top * NJ_INDEX_SIZE);
2246 que_id = GET_UINT16(p);
2247 eval = current;
2248
2249 for (i = (NJ_UINT16)psrhCache->storebuff[m].top; i <= (NJ_UINT16)psrhCache->storebuff[m].bottom; i++) {
2250 que_id = GET_UINT16(p);
2251 if (que_id < oldest) {
2252 eval = que_id + GET_LEARN_MAX_WORD_COUNT(loctset->loct.handle);
2253 } else {
2254 eval = que_id;
2255 }
2256 #ifdef LEARN_DEBUG
2257 printf("que(%d) : eval = %d : %d\n", que_id, eval, i);
2258 #endif
2259 if (eval >= max_value) {
2260 if ((GET_LOCATION_STATUS(loctset->loct.status) == NJ_ST_SEARCH_NO_INIT)
2261 || ((GET_LOCATION_STATUS(loctset->loct.status) == NJ_ST_SEARCH_READY)
2262 && (NJ_GET_AIMAI_FROM_SCACHE(psrhCache)))
2263 || (eval < current)) {
2264
2265
2266
2267 str = get_string(iwnn, loctset->loct.handle, que_id, &slen);
2268 if (str == NULL) {
2269 return NJ_SET_ERR_VAL(NJ_FUNC_SEARCH_RANGE_BY_YOMI, NJ_ERR_DIC_BROKEN);
2270 }
2271
2272
2273
2274 que = get_que_allHinsi(iwnn, loctset->loct.handle, que_id);
2275 if (njd_connect_test(cond, que->mae_hinsi, que->ato_hinsi)) {
2276
2277 loctset->loct.current_info = (NJ_UINT8)0x10;
2278 loctset->loct.current = i;
2279 max_value = eval;
2280 found = 1;
2281 #ifdef LEARN_DEBUG
2282 printf("---keep.");
2283 #endif
2284 }
2285 }
2286 }
2287 p += NJ_INDEX_SIZE;
2288 }
2289 }
2290 }
2291
2292 if (GET_LOCATION_STATUS(loctset->loct.status) != NJ_ST_SEARCH_NO_INIT) {
2293 NJ_UNSET_AIMAI_TO_SCACHE(psrhCache);
2294 }
2295
2296
2297 if (found == 0) {
2298 loctset->loct.status = NJ_ST_SEARCH_END;
2299 return 0;
2300 } else {
2301 loctset->loct.status = NJ_ST_SEARCH_READY;
2302 loctset->cache_freq = get_hindo(iwnn, loctset, search_pattern);
2303 return 1;
2304 }
2305 }
2306
search_range_by_yomi2(NJ_CLASS * iwnn,NJ_DIC_HANDLE handle,NJ_UINT8 op,NJ_CHAR * yomi,NJ_UINT16 len,NJ_UINT16 sfrom,NJ_UINT16 sto,NJ_UINT16 * from,NJ_UINT16 * to,NJ_UINT8 * forward_flag)2307 static NJ_INT16 search_range_by_yomi2(NJ_CLASS *iwnn, NJ_DIC_HANDLE handle, NJ_UINT8 op,
2308 NJ_CHAR *yomi, NJ_UINT16 len,
2309 NJ_UINT16 sfrom, NJ_UINT16 sto,
2310 NJ_UINT16 *from, NJ_UINT16 *to,
2311 NJ_UINT8 *forward_flag) {
2312 NJ_UINT16 right, mid = 0, left, max;
2313 NJ_UINT16 que_id;
2314 NJ_UINT8 *ptr, *p;
2315 NJ_CHAR *str;
2316 NJ_INT16 ret = 0;
2317 NJ_INT32 found = 0;
2318 NJ_UINT8 slen;
2319 NJ_INT32 cmp;
2320
2321
2322
2323 ptr = get_search_index_address(handle, op);
2324
2325 max = GET_LEARN_WORD_COUNT(handle);
2326
2327 right = sto;
2328 left = sfrom;
2329
2330 #ifdef LEARN_DEBUG
2331 printf("src:[%s]\n", yomi);
2332 #endif
2333
2334 *forward_flag = 0;
2335
2336 while (left <= right) {
2337 mid = left + ((right - left) / 2);
2338 p = ptr + (mid * NJ_INDEX_SIZE);
2339 que_id = GET_UINT16(p);
2340 str = get_string(iwnn, handle, que_id, &slen);
2341 if (str == NULL) {
2342 return NJ_SET_ERR_VAL(NJ_FUNC_SEARCH_RANGE_BY_YOMI, NJ_ERR_DIC_BROKEN);
2343 }
2344
2345
2346 ret = nj_strncmp(yomi, str, len);
2347
2348 #ifdef LEARN_DEBUG
2349 printf(" [%d][%d][%d]COMPARE:[%s] = %d\n", left, mid, right, str, ret);
2350 #endif
2351 if (ret == 0) {
2352
2353 found = 1;
2354 break;
2355 } else if (ret < 0) {
2356
2357 right = mid - 1;
2358 if (mid == 0) {
2359 break;
2360 }
2361 } else {
2362
2363 left = mid + 1;
2364 }
2365 }
2366
2367 if (!found) {
2368 return 0;
2369 }
2370
2371 if (mid == 0) {
2372 *from = mid;
2373 } else {
2374
2375 p = ((mid - 1) * NJ_INDEX_SIZE) + ptr;
2376
2377 for (cmp = mid - 1; cmp >= 0; cmp--) {
2378 que_id = GET_UINT16(p);
2379 str = get_string(iwnn, handle, que_id, &slen);
2380 if (str == NULL) {
2381 return NJ_SET_ERR_VAL(NJ_FUNC_SEARCH_RANGE_BY_YOMI, NJ_ERR_DIC_BROKEN);
2382 }
2383
2384
2385 if (nj_strncmp(yomi, str, len) != 0) {
2386 break;
2387 }
2388 p -= NJ_INDEX_SIZE;
2389 }
2390 if (cmp < 0) {
2391 *from = 0;
2392 } else {
2393 *from = (NJ_UINT16)cmp + 1;
2394 }
2395 }
2396
2397 #ifdef LEARN_DEBUG
2398 printf(" >> from:(%d)\n", *from);
2399 #endif
2400
2401 if ((mid + 1) >= max) {
2402 *to = mid;
2403 } else {
2404
2405 p = ((mid + 1) * NJ_INDEX_SIZE) + ptr;
2406
2407 for (right = mid + 1; right < max; right++) {
2408 que_id = GET_UINT16(p);
2409 str = get_string(iwnn, handle, que_id, &slen);
2410 if (str == NULL) {
2411 return NJ_SET_ERR_VAL(NJ_FUNC_SEARCH_RANGE_BY_YOMI, NJ_ERR_DIC_BROKEN);
2412 }
2413
2414
2415 if (nj_strncmp(yomi, str, len) != 0) {
2416 break;
2417 }
2418 p += NJ_INDEX_SIZE;
2419 }
2420 *to = right - 1;
2421 }
2422
2423 #ifdef LEARN_DEBUG
2424 printf(" >> to:(%d)\n", *to);
2425 #endif
2426 return 1;
2427 }
2428
2429