36 Commits

Author SHA1 Message Date
Vitaly Zdanevich
5478f290a1 README.org: fzf example: preview window make bigger
Was 50%:50% and by UX we do not need the half of the screen for the dictionary name.
2025-10-07 23:44:02 +03:00
Evgeniy A. Dushistov
9c77e91006 fix: include stdio for popen 2025-08-17 14:29:03 +03:00
Evgeniy A. Dushistov
b74bc2478a chore: document integration with readline
fixes #27
2025-08-17 14:22:40 +03:00
Vitaly Zdanevich
58c48988f6 README.org: add fzf 2025-08-17 13:58:02 +03:00
NorwayFun
07cd873e9d po: Adding Georgian translation 2025-08-17 13:52:26 +03:00
Evgeniy A. Dushistov
4545473da9 refactor: use more clear way to concat strings 2025-08-17 13:51:53 +03:00
Evgeniy A. Dushistov
849f0ed1ac fix: memory leak instroduced in #110 2025-08-17 13:51:53 +03:00
Evgeniy A. Dushistov
d5e1eb4d93 test: use actions/checkout@v4 2025-08-17 13:32:56 +03:00
Evgeniy A. Dushistov
3a4b76124c test: make sure cmake 3.10 works 2025-08-17 13:32:56 +03:00
Evgeniy A. Dushistov
6eaebaaa2f test: use cmake from distributive 2025-08-17 13:32:56 +03:00
Evgeniy A. Dushistov
e24722b8fc test: ubuntu 20.04 is missing, use 22.04 instead 2025-08-17 13:32:56 +03:00
Evgeniy A. Dushistov
c57ef6e916 fix: use READLINE_(INCLUDE_DIR|LIBRARY) if WITH_READLINE==True 2025-08-17 13:32:56 +03:00
Evgeniy A. Dushistov
24c08365c4 fix: set given invalid arguments for CACHE mode: missing type or docstring 2025-08-17 13:32:56 +03:00
Evgeniy A. Dushistov
8f77ede167 chore: update requirement for cmake to 3.10, to make modern cmake happy
and fix build on latest Ubuntu (24.04)
2025-08-17 13:32:56 +03:00
Evgeniy A. Dushistov
3a8ab1d5c3 test: install missed libglib2.0-dev on CI machine 2025-08-17 13:32:56 +03:00
Norayr Chilingarian
5887505185 Fix build with GCC 14 and modern glib: const correctness and deprecated API
- Use 'const gchar*' for result of g_utf8_next_char() to satisfy GCC 14's stricter const rules
- Remove incorrect g_free() on non-allocated pointer from g_utf8_next_char()
- Replace deprecated g_pattern_match_string() with g_pattern_spec_match_string()
2025-08-17 12:48:04 +03:00
Xiao Pan
beebb0faa7 fix: read_history() multiple times will add repeat histories to history lists
Issue Description:

When sdcv found multiple items, whatever your choice is, sdcv will add
double the current history entries to history file. For example, if
current history is "a\nb", you search akjk and there's multiple results,
whatever you choose, even -1,  after this is done, the history file will
be rewritten to "a\nb\nakjk\na\nb", note here \n is newline character.
So if you have 500 lines of history, you search akjk and there's
multiple results, you choose -1, after done there's 1001 lines of
history.

How to reproduce:

You can download this dictionary file
https://github.com/skywind3000/ECDICT/releases/download/1.0.28/ecdict-stardict-28.zip
and put into your dictionary directory, on Arch, with AUR, you can
install from https://aur.archlinux.org/packages/stardict-ecdict. Then,
make sure you also add the dictionary name to ~/.config/sdcv_ordering if
you have one. Add some lines to your history file if you do not have.
Then search for "akjk" with sdcv, e,g, `sdcv akjk`, then it will prompt
you to choose, you can choose -1, then ctrl-d to exit. Expected result
is history file add akjk at the end. Actual result is history file now
contain original content + akjk + original content duplicate as I
described in the issue description.

Fix and reasons:

I'm a hobbyist and I'm not a professional, I haven't use C++ for years
so many of my writings is very likely wrong. After some trail and error,
I found that call read_history() multiple times will add repeat
histories to history lists. In the commit d2327e2, a new IReadLine
object is created (note name changes, also note I know this description
of a IReadLine object is wrong). Here's a permalink:
49c8094b53/src/libwrapper.cpp (L418).
The problem of this new IReadLine object `choice_readline` is it called
read_history() again from ./src/readline.cpp constructor, because
there's already a IReadLine object `io` constructed at ./src/sdcv.cpp.
When read_history() is called twice, there's a "history lists" read from
history file first then append from history file again, so when you
destruct IReadLine object with write_history() in ./src/readline.cpp,
the history file contain duplicate content after write. Here are
permalinks:
49c8094b53/src/readline.cpp (L88),
and
49c8094b53/src/readline.cpp (L94).

So my fix is to just to use `io` IReadLine object and not to create a
new `choice_readline` object.

Misc:

During my trial and errors process, I made an example code to show
read_history()'s weird behavior. I did not dig deeper, I just guess
maybe there's some kind of werid history list as mentioned in
https://tiswww.cwru.edu/php/chet/readline/history.html#History-List-Management.

Here's the example code a.c, note you need to include stdio.h,
readline/history.h, and readline/readline.h. I did not include them here
because commit message seems will make them comment.
```c
...
int main (void)
{
	rl_readline_name="learn_readline";
	using_history();
	read_history("/home/xyz/test/learn_readline/history.txt");
	write_history("/home/xyz/test/learn_readline/history2.txt");
	{
		rl_readline_name="learn_readline";
		using_history();
		read_history("/home/xyz/test/learn_readline/history.txt");
		write_history("/home/xyz/test/learn_readline/history3.txt");
	}
	write_history("/home/xyz/test/learn_readline/history4.txt");
	return 0;
}
```
Here's the content of history.txt:
```
a
b
```
After build and run, as you can guess, history2.txt is same as
history.txt. But history3.txt and history4.txt content are:
```
a
b
a
b
```

Signed-off-by: Xiao Pan <xyz@flylightning.xyz>
2024-08-15 13:08:33 +03:00
Evgeniy A. Dushistov
49c8094b53 version 0.5.5 2023-04-18 21:47:55 +03:00
Evgeniy A. Dushistov
4346e65bd3 fix CI build: ubuntu-18.04 not supported by github actions anymore 2023-04-18 21:44:18 +03:00
Evgeniy A. Dushistov
d144e0310c fix CI build 2023-01-16 16:44:09 +03:00
NiLuJe
6e36e7730c Warn on unknown dicts 2022-09-16 18:48:08 +03:00
NiLuJe
abe5e9e72f Check accesses to the bookname_to_ifo std::map
Avoid crashes when passing unknown dicts to the -u flag

Fix #87
2022-09-16 18:48:08 +03:00
NiLuJe
488ec68854 Use off_t for stuff mainly assigned to a stat.st_size value
Allows simplifying the mmap sanity checks in mapfile, and actually
ensuring they won't break when -D_FILE_OFFSET_BITS=64
2022-09-14 22:12:29 +03:00
Marcelino Alberdi Pereira
b698445ead Add a small summary of the project to the README 2022-09-07 17:51:13 +03:00
Evgeniy A. Dushistov
504e7807e6 add information about 0.5.4 into NEWS 2022-06-24 21:49:00 +03:00
Evgeniy A. Dushistov
6c80bf2d99 t_json: add data about new dictionary 2022-06-24 21:34:47 +03:00
Evgeniy A. Dushistov
8742575c33 fix bash syntax error 2022-06-24 21:34:47 +03:00
Evgeniy A. Dushistov
b294b76fb5 check file size before mapping on linux 2022-06-24 21:34:47 +03:00
Evgeniy A. Dushistov
823ec3d840 clang-format for mapfile 2022-06-24 21:34:47 +03:00
Evgeniy A. Dushistov
6ab8b51e6c version 0.5.4 2022-06-24 21:34:47 +03:00
Evgeniy A. Dushistov
881657b336 Revert "replace deprecated g_pattern_match_string function"
This reverts commit 452a4e07fb.
2022-06-24 21:34:47 +03:00
Evgeniy A. Dushistov
911fc2f561 more robust parsing of ifo file
fixes #79 fixes #81
2022-06-24 21:34:47 +03:00
Evgeniy A. Dushistov
f488f5350b stardict_lib.hpp: remove unused headers plus clang-format 2022-06-24 21:34:47 +03:00
Evgeniy A. Dushistov
e72220e748 use cmake to check if compiler supports c++11 2022-06-24 21:34:47 +03:00
Evgeniy A. Dushistov
b77c0e793a replace deprecated g_pattern_match_string function 2022-06-24 21:34:47 +03:00
Evgeniy A. Dushistov
ebaa6f2136 clang-format for stardict_lib.cpp 2022-06-24 21:34:47 +03:00
11 changed files with 248 additions and 51 deletions

View File

@@ -20,14 +20,12 @@ jobs:
fail-fast: true
matrix:
os: [ubuntu-latest]
os: [ubuntu-22.04, ubuntu-latest]
steps:
- uses: actions/checkout@v2
- uses: actions/checkout@v4
- uses: jwlawson/actions-setup-cmake@v2
with:
submodules: 'recursive'
- uses: jwlawson/actions-setup-cmake@v1.4
with:
cmake-version: '3.5.1'
cmake-version: '3.10'
github-api-token: ${{ secrets.GITHUB_TOKEN }}
- name: Check versions
run: |
@@ -36,6 +34,10 @@ jobs:
gcc --version
echo "end of versions checking"
shell: bash
- uses: awalsh128/cache-apt-pkgs-action@v1
with:
packages: libglib2.0-dev
version: 1.0
- name: Run tests
run: |
set -e

View File

@@ -1,7 +1,7 @@
project(sdcv)
cmake_minimum_required(VERSION 3.10 FATAL_ERROR)
cmake_policy(VERSION 3.10)
cmake_minimum_required(VERSION 3.5 FATAL_ERROR)
cmake_policy(VERSION 3.5)
project(sdcv)
set(CMAKE_CXX_STANDARD 11)
set(CMAKE_CXX_STANDARD_REQUIRED True)
@@ -27,7 +27,8 @@ if (WITH_READLINE)
find_path(READLINE_INCLUDE_DIR readline/readline.h)
find_library(READLINE_LIBRARY NAMES readline)
if (NOT (READLINE_INCLUDE_DIR AND READLINE_LIBRARY))
set(WITH_READLINE False CACHE FORCE)
message(STATUS "readline library not FOUND, disable it's usage")
set(WITH_READLINE False CACHE BOOL "Use readline library" FORCE)
endif ()
endif (WITH_READLINE)
@@ -37,16 +38,16 @@ set(sdcv_SRCS
src/sdcv.cpp
src/readline.cpp
src/readline.hpp
src/libwrapper.cpp
src/libwrapper.cpp
src/libwrapper.hpp
src/utils.cpp
src/utils.cpp
src/utils.hpp
src/stardict_lib.cpp
src/stardict_lib.hpp
src/dictziplib.cpp
src/dictziplib.hpp
src/distance.cpp
src/dictziplib.hpp
src/distance.cpp
src/distance.hpp
src/mapfile.hpp
)
@@ -82,10 +83,13 @@ configure_file(${CMAKE_CURRENT_SOURCE_DIR}/config.h.cmake
include_directories(
${ZLIB_INCLUDE_DIR}
${GLIB2_INCLUDE_DIRS}
${READLINE_INCLUDE_DIR}
${CMAKE_CURRENT_SOURCE_DIR}/src/lib
${CMAKE_CURRENT_BINARY_DIR}
)
)
if (WITH_READLINE)
include_directories(${READLINE_INCLUDE_DIR})
endif()
#
# Packing stuff
@@ -95,7 +99,7 @@ set(CPACK_PACKAGE_VENDOR "Evgeniy Dushistov <dushistov@mail.ru>")
set(CPACK_PACKAGE_DESCRIPTION_FILE "${CMAKE_CURRENT_SOURCE_DIR}/README.org")
set(CPACK_PACKAGE_VERSION_MAJOR "0")
set(CPACK_PACKAGE_VERSION_MINOR "5")
set(CPACK_PACKAGE_VERSION_PATCH "4")
set(CPACK_PACKAGE_VERSION_PATCH "5")
set(sdcv_VERSION
"${CPACK_PACKAGE_VERSION_MAJOR}.${CPACK_PACKAGE_VERSION_MINOR}.${CPACK_PACKAGE_VERSION_PATCH}")
@@ -107,8 +111,10 @@ add_executable(sdcv ${sdcv_SRCS})
target_link_libraries(sdcv
${GLIB2_LIBRARIES}
${ZLIB_LIBRARIES}
${READLINE_LIBRARY}
)
if (WITH_READLINE)
target_link_libraries(sdcv ${READLINE_LIBRARY})
endif()
if (ENABLE_NLS)
set_directory_properties(PROPERTIES ADDITIONAL_MAKE_CLEAN_FILES "locale")
endif ()

12
NEWS
View File

@@ -1,3 +1,13 @@
Version 0.5.5
- Avoid crashes when passing unknown dicts to the -u flag (by NiLuJe)
- Use off_t for stuff mainly assigned to a stat.st_size value
Version 0.5.4
- Use binary search for synonyms
- Various improvments in work with synonyms
- Added --json (same as --json-output) to match man
- Show all matched result
- More robust parsing of ifo file
- Prevent crash if file size of files not matched expecting one for .oft files
Version 0.5.3
- Use single quotes around JSON data to reduce need for escaping
- Store integer magic in cache file
@@ -36,7 +46,7 @@ Version 0.4.2
* Russian translation update
Version 0.4.1
* Recreate cache if idx file was modified
* Recreate cache if idx file was modified
* Abbility to use pager(SDCV_PAGER)
* Add Chinese (traditional) translation
* Add Ukrainian translation

View File

@@ -1,6 +1,9 @@
#+OPTIONS: ^:nil
[[https://github.com/Dushistov/sdcv/actions?query=workflow%3ACI+branch%3Amaster][https://github.com/Dushistov/sdcv/workflows/CI/badge.svg]]
[[https://github.com/Dushistov/sdcv/blob/master/LICENSE][https://img.shields.io/badge/license-GPL%202-brightgreen.svg]]
* sdcv
*sdcv* is a simple, cross-platform, text-based utility for working with dictionaries in [[http://stardict-4.sourceforge.net/][StarDict]] format.
* How to compile and install
#+BEGIN_SRC sh
mkdir /tmp/build-sdcv
@@ -26,6 +29,26 @@ To report bugs use https://github.com/Dushistov/sdcv/issues ,
if it is not possible you can report it via email to dushistov at mail dot ru.
Be sure to include the word "sdcv" somewhere in the "Subject:" field.
* Integration with [[https://github.com/junegunn/fzf][fzf]]
Useful when you have multiple dictionaries
#+BEGIN_SRC sh
fzf --prompt="Dict: " \
--phony \
--bind "enter:reload(sdcv {q} -n --json | jq '.[].dict' -r)" \
--preview "sdcv {q} -en --use-dict={}" \
--preview-window=right:70%:wrap \
< <(echo)
#+END_SRC
* Integration with readline
This lines can be added to inputrc file (~/.inputrc, /etc/inputrc),
to abort multiply usage with ESC:
#+begin_src
$if sdcv
"\e\e": "-1\n"
$endif
#+end_src
* Notes to developer
** make source code release
#+BEGIN_SRC sh

147
po/ka.po Normal file
View File

@@ -0,0 +1,147 @@
# Georgian translation for sdcv.
# Copyright (C) 2025 sdcv authors
# This file is distributed under the same license as the sdcv project.
# Temuri Doghonadze <temuri.doghonadze@gmail.com>, 2025.
#
msgid ""
msgstr ""
"Project-Id-Version: sdcv 0.5\n"
"Report-Msgid-Bugs-To: dushistov@mail.ru\n"
"POT-Creation-Date: 2020-08-14 12:58+0300\n"
"PO-Revision-Date: 2025-01-26 03:17+0100\n"
"Last-Translator: Temuri Doghonadze <temuri.doghonadze@gmail.com>\n"
"Language-Team: Georgian <(nothing)>\n"
"Language: ka\n"
"MIME-Version: 1.0\n"
"Content-Type: text/plain; charset=UTF-8\n"
"Content-Transfer-Encoding: 8bit\n"
"X-Generator: Poedit 3.5\n"
#: ../src/libwrapper.cpp:300
msgid "popen failed"
msgstr "popen ჩავარდა"
#: ../src/libwrapper.cpp:341
#, c-format
msgid "Can not convert %s to utf8.\n"
msgstr "%s-ის utf8-ში გადაყვანა შეუძლებელია.\n"
#: ../src/libwrapper.cpp:399 ../src/libwrapper.cpp:433
#, c-format
msgid "Found %zu items, similar to %s.\n"
msgstr "აღმოჩენილია %zu ელემენტი, რომელიც %s-ს ჰგავს.\n"
#: ../src/libwrapper.cpp:417
msgid "Your choice[-1 to abort]: "
msgstr "თქვენი არჩევანი[-1 გასაუქმებლად]: "
#: ../src/libwrapper.cpp:427
#, c-format
msgid ""
"Invalid choice.\n"
"It must be from 0 to %zu or -1.\n"
msgstr ""
"არასწორი არჩევანი.\n"
"უნდა იყოს 0-დან %zu-მდე, ან -1.\n"
#: ../src/libwrapper.cpp:446
#, c-format
msgid "Nothing similar to %s, sorry :(\n"
msgstr "%s-ს არაფერი ჰგავს :(\n"
#: ../src/sdcv.cpp:89
msgid "display version information and exit"
msgstr "ვერსიის ჩვენება და გასვლა"
#: ../src/sdcv.cpp:91
msgid "display list of available dictionaries and exit"
msgstr "ხელმისაწვდომი ლექსიკონების ჩვენება და გასვლა"
#: ../src/sdcv.cpp:93
msgid "for search use only dictionary with this bookname"
msgstr "ძებნისთვის, მხოლოდ, ამ სახელის მქონე ლექსიკონის გამოყენება"
#: ../src/sdcv.cpp:94
msgid "bookname"
msgstr "ლექსიკონის_სახელი"
#: ../src/sdcv.cpp:96
msgid "for use in scripts"
msgstr "სკრიპტებში გამოსაყენებლად"
#: ../src/sdcv.cpp:98
msgid "print the result formatted as JSON"
msgstr "შედეგების JSON ფორმატში გამოტანა"
#: ../src/sdcv.cpp:100
msgid "do not fuzzy-search for similar words, only return exact matches"
msgstr ""
"მსგავსი სიტყვებისთვის არაზუსტი ძებნა გამოყენებული არ იქნება. "
"დაბრუნდება, მხოლოდ, ზუსტი დამთხვევები"
#: ../src/sdcv.cpp:102
msgid "output must be in utf8"
msgstr "გამოტანა utf8-ში უნდა იყოს"
#: ../src/sdcv.cpp:104
msgid "input of sdcv in utf8"
msgstr "პროგრამაში შეყვანა utf8 -ში"
#: ../src/sdcv.cpp:106
msgid "use this directory as path to stardict data directory"
msgstr ""
"ამ საქაღალდის გამოყენება stardict-ის მონაცემების საქაღალდის ბილიკად"
#: ../src/sdcv.cpp:107
msgid "path/to/dir"
msgstr "ბილიკი/სასურველ/საქაღალდემდე"
#: ../src/sdcv.cpp:109
msgid ""
"only use the dictionaries in data-dir, do not search in user and system "
"directories"
msgstr ""
"ლექსიკონების, მხოლოდ, data-dir-დან გამოყენება. მომხმარებლის და სისტემურ "
"საქაღალდეებში ძებნა არ მოხდება"
#: ../src/sdcv.cpp:111
msgid "colorize the output"
msgstr "ფერებში გამოტანა"
#: ../src/sdcv.cpp:116
msgid " words"
msgstr " სიტყვა"
#: ../src/sdcv.cpp:122
#, c-format
msgid "Invalid command line arguments: %s\n"
msgstr "არასწორი ბრძანების სტრიქონის არგუმენტები: %s\n"
#: ../src/sdcv.cpp:128
#, c-format
msgid "Console version of Stardict, version %s\n"
msgstr "Startdict-ის კონსოლის ვერსია. ვერსია %s\n"
#: ../src/sdcv.cpp:206
#, c-format
msgid "g_mkdir failed: %s\n"
msgstr "g_mkdir ჩავარდა: %s\n"
#: ../src/sdcv.cpp:222
msgid "Enter word or phrase: "
msgstr "შეიყვანეთ სიტყვა ან ფრაზა: "
#: ../src/sdcv.cpp:230
#, c-format
msgid "There are no words/phrases to translate.\n"
msgstr "სათარგმნი სიტყვების/ფრაზების გარეშე.\n"
#: ../src/sdcv.cpp:242
#, c-format
msgid "Dictionary's name Word count\n"
msgstr "ლექსიკონის სახელი სიტყვების რაოდენობა\n"
#: ../src/utils.cpp:48
#, c-format
msgid "Can not convert %s to current locale.\n"
msgstr "ვერ გადავიყვანე %s მიმდინარე ლოკალში.\n"

View File

@@ -27,7 +27,7 @@ public:
private:
const char *start; /* start of mmap'd area */
const char *end; /* end of mmap'd area */
unsigned long size; /* size of mmap */
off_t size; /* size of mmap */
int type;
z_stream zStream;
@@ -47,7 +47,7 @@ private:
std::string origFilename;
std::string comment;
unsigned long crc;
unsigned long length;
off_t length;
unsigned long compressedLength;
DictCache cache[DICT_CACHE_SIZE];
MapFile mapfile;

View File

@@ -23,6 +23,7 @@
#endif
#include <cstring>
#include <cstdio> //for popen
#include <map>
#include <memory>
@@ -415,10 +416,9 @@ search_result Library::process_phrase(const char *loc_str, IReadLine &io, bool f
colorize_output_ ? ESC_END : "");
}
int choise;
std::unique_ptr<IReadLine> choice_readline(create_readline_object());
for (;;) {
std::string str_choise;
choice_readline->read(_("Your choice[-1 to abort]: "), str_choise);
io.read(_("Your choice[-1 to abort]: "), str_choise);
sscanf(str_choise.c_str(), "%d", &choise);
if (choise >= 0 && choise < int(res_list.size())) {
sdcv_pager pager;

View File

@@ -22,13 +22,13 @@ public:
~MapFile();
MapFile(const MapFile &) = delete;
MapFile &operator=(const MapFile &) = delete;
bool open(const char *file_name, unsigned long file_size);
bool open(const char *file_name, off_t file_size);
gchar *begin() { return data; }
private:
char *data = nullptr;
unsigned long size = 0ul;
#ifdef HAVE_MMAP
size_t size = 0u;
int mmap_fd = -1;
#elif defined(_WIN32)
HANDLE hFile = 0;
@@ -36,9 +36,8 @@ private:
#endif
};
inline bool MapFile::open(const char *file_name, unsigned long file_size)
inline bool MapFile::open(const char *file_name, off_t file_size)
{
size = file_size;
#ifdef HAVE_MMAP
if ((mmap_fd = ::open(file_name, O_RDONLY)) < 0) {
// g_print("Open file %s failed!\n",fullfilename);
@@ -46,14 +45,16 @@ inline bool MapFile::open(const char *file_name, unsigned long file_size)
}
struct stat st;
if (fstat(mmap_fd, &st) == -1 || st.st_size < 0 || (st.st_size == 0 && S_ISREG(st.st_mode))
|| sizeof(st.st_size) > sizeof(file_size) || static_cast<unsigned long>(st.st_size) != file_size) {
|| st.st_size != file_size) {
close(mmap_fd);
return false;
}
data = (gchar *)mmap(nullptr, file_size, PROT_READ, MAP_SHARED, mmap_fd, 0);
size = static_cast<size_t>(st.st_size);
data = (gchar *)mmap(nullptr, size, PROT_READ, MAP_SHARED, mmap_fd, 0);
if ((void *)data == (void *)(-1)) {
// g_print("mmap file %s failed!\n",idxfilename);
size = 0u;
data = nullptr;
return false;
}

View File

@@ -186,10 +186,13 @@ try {
}
// add bookname to list
gchar **p = get_impl(use_dict_list);
while (*p) {
order_list.push_back(bookname_to_ifo.at(*p));
++p;
for (gchar **p = get_impl(use_dict_list); *p != nullptr; ++p) {
auto it = bookname_to_ifo.find(*p);
if (it != bookname_to_ifo.end()) {
order_list.push_back(it->second);
} else {
fprintf(stderr, _("Unknown dictionary: %s\n"), *p);
}
}
} else {
std::string ordering_cfg_file = std::string(g_get_user_config_dir()) + G_DIR_SEPARATOR_S "sdcv_ordering";
@@ -201,7 +204,12 @@ try {
if (ordering_file != nullptr) {
std::string line;
while (stdio_getline(ordering_file, line)) {
order_list.push_back(bookname_to_ifo.at(line));
auto it = bookname_to_ifo.find(line);
if (it != bookname_to_ifo.end()) {
order_list.push_back(it->second);
} else {
fprintf(stderr, _("Unknown dictionary: %s\n"), line.c_str());
}
}
fclose(ordering_file);
}

View File

@@ -429,7 +429,7 @@ public:
if (idxfile)
fclose(idxfile);
}
bool load(const std::string &url, gulong wc, gulong fsize, bool verbose) override;
bool load(const std::string &url, gulong wc, off_t fsize, bool verbose) override;
const gchar *get_key(glong idx) override;
void get_data(glong idx) override { get_key(idx); }
const gchar *get_key_and_data(glong idx) override
@@ -489,7 +489,7 @@ public:
{
}
~WordListIndex() { g_free(idxdatabuf); }
bool load(const std::string &url, gulong wc, gulong fsize, bool verbose) override;
bool load(const std::string &url, gulong wc, off_t fsize, bool verbose) override;
const gchar *get_key(glong idx) override { return wordlist[idx]; }
void get_data(glong idx) override;
const gchar *get_key_and_data(glong idx) override
@@ -615,7 +615,7 @@ bool OffsetIndex::save_cache(const std::string &url, bool verbose)
return false;
}
bool OffsetIndex::load(const std::string &url, gulong wc, gulong fsize, bool verbose)
bool OffsetIndex::load(const std::string &url, gulong wc, off_t fsize, bool verbose)
{
wordcount = wc;
gulong npages = (wc - 1) / ENTR_PER_PAGE + 2;
@@ -758,7 +758,7 @@ bool OffsetIndex::lookup(const char *str, std::set<glong> &idxs, glong &next_idx
return bFound;
}
bool WordListIndex::load(const std::string &url, gulong wc, gulong fsize, bool)
bool WordListIndex::load(const std::string &url, gulong wc, off_t fsize, bool)
{
gzFile in = gzopen(url.c_str(), "rb");
if (in == nullptr)
@@ -771,7 +771,7 @@ bool WordListIndex::load(const std::string &url, gulong wc, gulong fsize, bool)
if (len < 0)
return false;
if (gulong(len) != fsize)
if (static_cast<off_t>(len) != fsize)
return false;
wordlist.resize(wc + 1);
@@ -920,7 +920,7 @@ bool Dict::Lookup(const char *str, std::set<glong> &idxs, glong &next_idx)
bool Dict::load(const std::string &ifofilename, bool verbose)
{
gulong idxfilesize;
off_t idxfilesize;
if (!load_ifofile(ifofilename, idxfilesize))
return false;
@@ -964,7 +964,7 @@ bool Dict::load(const std::string &ifofilename, bool verbose)
return true;
}
bool Dict::load_ifofile(const std::string &ifofilename, gulong &idxfilesize)
bool Dict::load_ifofile(const std::string &ifofilename, off_t &idxfilesize)
{
DictInfo dict_info;
if (!dict_info.load_from_ifo_file(ifofilename, false))
@@ -989,7 +989,7 @@ bool Dict::LookupWithRule(GPatternSpec *pspec, glong *aIndex, int iBuffLen)
int iIndexCount = 0;
for (guint32 i = 0; i < narticles() && iIndexCount < (iBuffLen - 1); i++)
if (g_pattern_match_string(pspec, get_key(i)))
if (g_pattern_spec_match_string(pspec, get_key(i)))
aIndex[iIndexCount++] = i;
aIndex[iIndexCount] = -1; // -1 is the end.
@@ -1047,12 +1047,12 @@ bool Libs::LookupSimilarWord(const gchar *sWord, std::set<glong> &iWordIndices,
}
// Upper the first character and lower others.
if (!bFound) {
gchar *nextchar = g_utf8_next_char(sWord);
gchar *firstchar = g_utf8_strup(sWord, nextchar - sWord);
nextchar = g_utf8_strdown(nextchar, -1);
casestr = g_strdup_printf("%s%s", firstchar, nextchar);
const gchar *rest = g_utf8_next_char(sWord);
gchar *firstchar = g_utf8_strup(sWord, rest - sWord);
gchar *rest_lowercase = g_utf8_strdown(rest, -1);
casestr = g_strconcat(firstchar, rest_lowercase, nullptr);
g_free(rest_lowercase);
g_free(firstchar);
g_free(nextchar);
if (strcmp(casestr, sWord)) {
if (oLib[iLib]->Lookup(casestr, iWordIndices))
bFound = true;

View File

@@ -77,8 +77,8 @@ struct DictInfo {
std::string website;
std::string date;
std::string description;
guint32 index_file_size;
guint32 syn_file_size;
off_t index_file_size;
off_t syn_file_size;
std::string sametypesequence;
bool load_from_ifo_file(const std::string &ifofilename, bool istreedict);
@@ -91,7 +91,7 @@ public:
guint32 wordentry_size;
virtual ~IIndexFile() {}
virtual bool load(const std::string &url, gulong wc, gulong fsize, bool verbose) = 0;
virtual bool load(const std::string &url, gulong wc, off_t fsize, bool verbose) = 0;
virtual const gchar *get_key(glong idx) = 0;
virtual void get_data(glong idx) = 0;
virtual const gchar *get_key_and_data(glong idx) = 0;
@@ -160,7 +160,7 @@ private:
std::unique_ptr<IIndexFile> idx_file;
std::unique_ptr<SynFile> syn_file;
bool load_ifofile(const std::string &ifofilename, gulong &idxfilesize);
bool load_ifofile(const std::string &ifofilename, off_t &idxfilesize);
};
class Libs