inih (INI Not Invented Here)は、C で書かれたシンプルな .INI ファイル パーサーです。コードは数ページのみで、小さくシンプルになるように設計されているため、組み込みシステムに適しています。また、RFC 822 スタイルの複数行構文やname: value
エントリなど、Python の ConfigParser スタイルの .INI ファイルと多かれ少なかれ互換性があります。
これを使用するには、 ini_parse()
に INI ファイルを与えるだけで、解析されたすべてのname=value
ペアに対してコールバックが呼び出され、セクション、名前、および値の文字列が得られます。この方法 (「SAX スタイル」) で行われるのは、この方法が低メモリの組み込みシステムでうまく機能するためですが、また、KISS の実装にも適しているためです。
また、 ini_parse_file()
を呼び出してFILE*
オブジェクトから直接解析したり、 ini_parse_string()
呼び出して文字列からデータを解析したり、 ini_parse_stream()
を呼び出してカスタム I/O 用のカスタム fgets スタイルのリーダー関数を使用して解析したりすることもできます。
リリースをダウンロードし、ソースを参照するか、X-Macros を使用して DRY スタイルで inih を使用する方法について読んでください。
プリプロセッサの定義を使用して、inih のさまざまな側面を制御できます。
-DINI_ALLOW_MULTILINE=0
を追加します。-DINI_ALLOW_BOM=0
を追加します。;
キャラクター。無効にするには、 -DINI_ALLOW_INLINE_COMMENTS=0
を追加します。 INI_INLINE_COMMENT_PREFIXES
を使用して、インライン コメントを開始する文字を指定することもできます。;
および#
は行の先頭でコメントを開始します。 INI_START_COMMENT_PREFIXES
変更することでこれをオーバーライドできます。=
または:
がない) をエラーとして扱います。値のない名前を許可するには、 -DINI_ALLOW_NO_VALUE=1
を追加すると、inih は値を NULL に設定してハンドラー関数を呼び出します。-DINI_STOP_ON_FIRST_ERROR=1
を追加します。ini_handler
コールバックはパラメータとして行番号を受け取りません。必要な場合は、 -DINI_HANDLER_LINENO=1
を追加します。name=value
ペアでのみハンドラーを呼び出します。新しいセクション (たとえば、INI ファイルに同じ名前の複数のセクションがある) を検出するには、 -DINI_CALL_HANDLER_ON_NEW_SECTION=1
を追加します。新しいセクションが見つかるたびにハンドラー関数が呼び出され、 section
には新しいセクション名が設定されますが、 name
とvalue
NULL に設定されます。malloc
使用してヒープに割り当てるには、 -DINI_USE_STACK=0
を指定します。-DINI_MAX_LINE=1000
のようなものを追加します。 INI_MAX_LINE
最長行より 3 つ多くなければならないことに注意してください ( r
、 n
、および NUL のため)。INI_INITIAL_ALLOC
ヒープを使用するときの初期の malloc サイズを指定します。デフォルトは 200 バイトです。-DINI_USE_STACK=0
)、inih はINI_INITIAL_ALLOC
バイトの固定サイズのバッファーを割り当てます。これをINI_MAX_LINE
バイト (必要に応じて 2 倍) まで拡大できるようにするには、 -DINI_ALLOW_REALLOC=1
設定します。malloc
、 free
、およびrealloc
関数が使用されます。カスタム アロケータを使用するには、 -DINI_CUSTOM_ALLOCATOR=1
(および-DINI_USE_STACK=0
) を指定します。 ini_malloc
、 ini_free
、および ( INI_ALLOW_REALLOC
が設定されている場合) ini_realloc
という名前の関数を定義してリンクする必要があります。これらの関数は、 stdlib.h
メモリ割り当て関数と同じシグネチャを持つ必要があります。 #include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include "../ini.h"
typedef struct
{
int version ;
const char * name ;
const char * email ;
} configuration ;
static int handler ( void * user , const char * section , const char * name ,
const char * value )
{
configuration * pconfig = ( configuration * ) user ;
#define MATCH ( s , n ) strcmp(section, s) == 0 && strcmp(name, n) == 0
if ( MATCH ( "protocol" , "version" )) {
pconfig -> version = atoi ( value );
} else if ( MATCH ( "user" , "name" )) {
pconfig -> name = strdup ( value );
} else if ( MATCH ( "user" , "email" )) {
pconfig -> email = strdup ( value );
} else {
return 0 ; /* unknown section/name, error */
}
return 1 ;
}
int main ( int argc , char * argv [])
{
configuration config ;
if ( ini_parse ( "test.ini" , handler , & config ) < 0 ) {
printf ( "Can't load 'test.ini'n" );
return 1 ;
}
printf ( "Config loaded from 'test.ini': version=%d, name=%s, email=%sn" ,
config . version , config . name , config . email );
return 0 ;
}
C++ と STL に興味がある場合は、値をmap
に保存してGet()
できる、使いやすい INIReader クラスもあります。
# include < iostream >
# include " INIReader.h "
int main ()
{
INIReader reader ( " ../examples/test.ini " );
if (reader. ParseError () < 0 ) {
std::cout << " Can't load 'test.ini' n " ;
return 1 ;
}
std::cout << " Config loaded from 'test.ini': version= "
<< reader. GetInteger ( " protocol " , " version " , - 1 ) << " , name= "
<< reader. Get ( " user " , " name " , " UNKNOWN " ) << " , email= "
<< reader. Get ( " user " , " email " , " UNKNOWN " ) << " , pi= "
<< reader. GetReal ( " user " , " pi " , - 1 ) << " , active= "
<< reader. GetBoolean ( " user " , " active " , true ) << " n " ;
return 0 ;
}
この単純な C++ API は問題なく動作しますが、完全なものではありません。現時点では C++ API にさらに取り組む予定はないため、もう少し機能が必要な場合 (たとえば、 GetSections()
関数やGetFields()
関数)、次のフォークを参照してください。
inih と Python の ConfigParser 標準ライブラリ モジュールのいくつかの違い:
_wfopen()
呼び出してファイルを開き、次にini_parse_file()
てそれを解析する必要があります。 inih には、 wchar_t
または Unicode 処理は含まれません。 meson.build
ファイルは、inih を使用したりコンパイルしたりする必要はありません。その主な目的はディストリビューションです。-Ddefault_library=static
指定すると、静的ライブラリが構築されます。-Ddistro_install=false
指定すると、ライブラリ、ヘッダー、および pkg-config ファイルはインストールされません。-Dwith_INIReader=false
を使用すると、C++ ライブラリのビルドを無効にできます。distro_install
がtrue
に設定されている場合、これらは機能しません。inih
およびINIReader
です。inih_dep
およびINIReader_dep
依存関係変数を使用できます。サブプロジェクトに対して、 default_library=static
およびdistro_install=false
を設定することもできます。公式の Wrap は WrapDB で提供されています。project()
関数のlicense
タグの後にversion : '<version_as_int>',
を追加し、両方のlibrary()
関数のsoversion
タグの後にversion : meson.project_version(),
を追加します。 inih
、次のエントリを.tipi/deps
に追加するだけで、tipi.build プロジェクトで簡単に使用できます ( r56
最新バージョンのタグに置き換えます)。
{
"benhoyt/inih" : { "@" : " r56 " }
}
プロジェクトに必要なインクルード パスは次のとおりです。
#include <ini.h>
vcpkg 依存関係マネージャーを使用して、inih をビルドしてインストールできます。
git clone https://github.com/Microsoft/vcpkg.git
cd vcpkg
./bootstrap-vcpkg.sh
./vcpkg integrate install
./vcpkg install inih
vcpkg の inih ポートは、Microsoft チームのメンバーとコミュニティの貢献者によって最新の状態に保たれています。バージョンが古い場合は、vcpkg リポジトリで問題を作成するか、プル リクエストを作成してください。