XMLPars.c

C:\home\SVGCats_src\src\XMLPars.c

[大目次 | 目次 | 関数]

大目次

目次

関数一覧


   1|/**************************************************************************
   2|  1. <<< XMLパーサ (XMLPars)  >>> 
   3|***************************************************************************/
   4|
   5|#include "mixer_precomp.h"
   6|
   7|#ifdef  USES_MXP_AUTOINC
   8| #include  <XMLPars.ah>  /* Auto include header, Look at mixer-... folder */
   9|#endif
  10|
  11|
  12| 
  13|/*---------------------------------------------------------------------*/
  14|/* 2. <<<<◆(XMLPars) XMLパーサ >>>> */ 
  15|/*---------------------------------------------------------------------*/
  16|
  17| 
  18|/**************************************************************************
  19|  2-1. <<< [XMLPars_init] 初期化する >>> 
  20|【引数】
  21|  ・XMLPars*  m;   XMLパーサ
  22|  ・char*  path;   読み込むファイルのパス
  23|  ・void*  buf;    タグ解析用バッファ(→補足)
  24|  ・int  buf_size;   buf のサイズ(バイト)
  25|【補足】
  26|・buf_size は、3072ぐらいを設定します。 buf は、1つのタグの最大バイト数と
  27|  1つのタグの最大属性数(40固定)*8 と、BLex3_Engine で使用するバッファの
  28|  サイズ(1024固定)*2 の合計です。
  29|・本関数を呼び出した後、XMLPars_parse を呼び出して初めて、XMLPars_getTagName
  30|  などを呼び出すことができます。
  31|***************************************************************************/
  32|void  XMLPars_init( XMLPars* m, const char* path, void* buf, int buf_size )
  33|{
  34|  enum { eng_buf_size = 1024,  mAttr = 40, mem2_size = mAttr*2*sizeof(char*) };
  35|
  36|  ERRORS_INITCHK( m, 0 );
  37|  ASSERT( buf_size >= eng_buf_size*2 + mem2_size + 40 );
  38|
  39|  BLex3_Engine_init( &m->engU.inherit_BLex3_Engine, path, buf, eng_buf_size, 256 );
  40|  BLex3_Engine_setSJisBuf( &m->engU.inherit_BLex3_Engine, (char*)buf + eng_buf_size,
  41|    eng_buf_size );
  42|
  43|  LineCnt_init( &m->lineCnt );
  44|  LineCnt_linkEngine( &m->lineCnt, &m->engU.inherit_BLex3_Engine );
  45|
  46|  HtmlPars_init( &m->htmlPars,
  47|    (char*)buf + eng_buf_size*2 + mem2_size,
  48|    buf_size - eng_buf_size*2 - mem2_size,
  49|    (char**)( (char*)buf + eng_buf_size*2 ),
  50|    mem2_size );
  51|  HtmlPars_linkEngine( &m->htmlPars, &m->engU );
  52|
  53|  m->bText = false;
  54|  m->spaceTagName[0] = '\0';
  55|
  56|  ERRORS_FINISHCHK_FOR_INIT( XMLPars_finish );
  57|}
  58|
  59|
  60| 
  61|/**************************************************************************
  62|  2-2. <<< [XMLPars_finish] 後始末する >>> 
  63|***************************************************************************/
  64|void  XMLPars_finish( XMLPars* m )
  65|{
  66|  ERRORS_INITCHK( m, 1 );
  67|  ERRORS_FINISHCHK_FOR_FINISH( XMLPars_finish );
  68|
  69|  BLex3_Engine_finish( &m->engU.inherit_BLex3_Engine );
  70|}
  71|
  72|
  73| 
  74|/**************************************************************************
  75|  2-3. <<< [XMLPars_parse] 字句解析を行う。次のタグ等へ移動する >>> 
  76|【引数】
  77|  ・XMLPars*  m;   XMLパーサ
  78|  ・bool  返り値;  次のタグ等があったかどうか(ファイルの末尾でないか)
  79|***************************************************************************/
  80|bool  XMLPars_parse( XMLPars* m )
  81|{
  82|  BLex3_Pos  pos;
  83|  BLex3_Engine*  eng = &m->engU.inherit_BLex3_Engine;
  84|
  85|  ERRORS_INITCHK( m, 1 );
  86|
  87|  m->bText = false;
  88|
  89|  /* パース */
  90|  do {
  91|    BLex3_Engine_setPos( eng, &m->htmlPars.parsedPos );
  92|    BLex3_Pos_copy( &pos, &m->htmlPars.parsedPos );
  93|    if ( BLex3_Engine_getFilePtr( eng, 0 ) == NULL )
  94|      return  false;
  95|    HtmlPars_parse( &m->htmlPars );
  96|
  97|    /* タグ間のテキストがあるかどうかを調べる */
  98|    if ( HtmlPars_getTokenType( &m->htmlPars ) == HtmlPars_EndOfTag ) {
  99|      char*  fp;
 100|      char*  xml_space;
 101|
 102|      BLex3_Engine_setPos( eng, &m->htmlPars.parsedPos );
 103|      if ( m->spaceTagName[0] == '\0' ) {
 104|        xml_space = HtmlPars_getValue( &m->htmlPars, "xml:space" );
 105|        if ( xml_space != NULL && strcmp( xml_space, "preserve" ) == 0 )
 106|          strcpy( m->spaceTagName, HtmlPars_getName( &m->htmlPars ) );
 107|      }
 108|      else if ( strcmp( m->spaceTagName, HtmlPars_getName( &m->htmlPars )+1 ) == 0 ) {
 109|        if ( HtmlPars_getName( &m->htmlPars )[0] == '/' )
 110|          m->spaceTagName[0] = '\0';
 111|      }
 112|      if ( m->spaceTagName[0] == '\0' )
 113|        BLex3_EngineU_skip( &m->engU, " \t\r\n" );
 114|      else
 115|        BLex3_EngineU_skip( &m->engU, "\r\n" );
 116|
 117|      fp = BLex3_Engine_getFilePtr( eng, 1 );
 118|      if ( fp == NULL )  return  false;
 119|      if ( *fp != '<' || m->htmlPars.endCh == '\0' ) {
 120|        BLex3_Engine_getPos( eng, &pos );
 121|        m->bText = true;
 122|        break;
 123|      }
 124|      else
 125|        continue;
 126|    }
 127|  } while ( HtmlPars_getTokenType( &m->htmlPars ) != HtmlPars_StartOfTag );
 128|
 129|  BLex3_Engine_setPos( eng, &pos );
 130|  LineCnt_parse( &m->lineCnt );
 131|
 132|  return  true;
 133|}
 134|
 135|
 136| 
 137|/**************************************************************************
 138|  2-4. <<< [XMLPars_getTokenType] 現在位置のXMLトークンタイプを返す >>> 
 139|【引数】
 140|  ・XMLPars*  m;   XMLパーサ
 141|  ・int  返り値;   XMLトークンタイプ
 142|***************************************************************************/
 143|int  XMLPars_getTokenType( XMLPars* m )
 144|{
 145|  ERRORS_INITCHK( m, 1 );
 146|
 147|  if ( m->bText )
 148|    return  XMLPars_TextBetweenTags;
 149|
 150|  else if ( m->htmlPars.endCh == '/' || m->htmlPars.endCh == '?' )
 151|    return  XMLPars_StartAndEndTag;
 152|
 153|  else if ( XMLPars_getTagName( m )[0] == '/' )
 154|    return  XMLPars_EndTag;
 155|
 156|  else if ( XMLPars_getTagName( m )[0] == '!' )
 157|    return  XMLPars_StartAndEndTag;
 158|
 159|  else
 160|    return  XMLPars_StartTag;
 161|}
 162|
 163|
 164| 
 165|/**************************************************************************
 166|  2-5. <<< [XMLPars_getTagName] 現在位置のタグの名前を返す >>> 
 167|【引数】
 168|  ・XMLPars*  m;    XMLパーサ
 169|  ・char*  返り値;  現在位置のタグの名前
 170|【補足】
 171|・返り値は、本クラスを初期化したときに指定した領域の内部を指しています。
 172|・XMLPars_TextBetweenTags のときは、そのテキストを囲むタグの名前を返します。
 173|・XMLPars_EndTag のときは、先頭に '/' の付いた名前を返します。
 174|***************************************************************************/
 175|char*  XMLPars_getTagName( XMLPars* m )
 176|{
 177|  ERRORS_INITCHK( m, 1 );
 178|
 179|  return  HtmlPars_getName( &m->htmlPars );
 180|}
 181|
 182|
 183| 
 184|/**************************************************************************
 185|  2-6. <<< [XMLPars_getValue] 現在位置のタグの中の属性の値を返す >>> 
 186|【引数】
 187|  ・XMLPars*  m;    XMLパーサ
 188|  ・char*  name;    属性の名前
 189|  ・char*  返り値;  属性の値(NULL=該当する属性が無い)
 190|【補足】
 191|・返り値は、本クラスを初期化したときに指定した領域の内部を指しています。
 192|***************************************************************************/
 193|char*  XMLPars_getValue( XMLPars* m, const char* name )
 194|{
 195|  ERRORS_INITCHK( m, 1 );
 196|
 197|  return  HtmlPars_getValue( &m->htmlPars, name );
 198|}
 199|
 200|
 201| 
 202|/**************************************************************************
 203|  2-7. <<< [XMLPars_getText] 現在位置のタグの間のテキストを取得する >>> 
 204|【引数】
 205|  ・XMLPars*  m;    XMLパーサ
 206|  ・int  offset;    取得する位置をテキストの先頭から offset だけ足す
 207|  ・char*     s;    テキストを格納する領域のアドレス
 208|  ・int  s_size;    s のサイズ(バイト)
 209|  ・int  返り値;    格納したテキストのサイズ(0=offset が大きいかテキストが無い)
 210|【補足】
 211|・s より大きな領域を複数に分けて取得するときは、返り値が 0になるまで
 212|  offset を足して、繰り返し本関数を呼び出してください。
 213|***************************************************************************/
 214|int  XMLPars_getText( XMLPars* m, int offset, char* s, int s_size )
 215|{
 216|  BLex3_Pos  pos;
 217|  char*  xml_space;
 218|
 219|  XMLPars_getPos( m, &pos );
 220|  BLex3_Engine_setPos2( &m->engU.inherit_BLex3_Engine, &pos, offset );
 221|  BLex3_EngineU_readWord( &m->engU, s, s_size, "<", false );
 222|  xml_space = HtmlPars_getValue( &m->htmlPars, "xml:space" );
 223|  if ( m->spaceTagName[0] == '\0' )
 224|    StrX_trim( s );
 225|
 226|  return  strlen(s);
 227|}
 228|
 229| 
 230|/***********************************************************************
 231|  2-8. <<< [XMLPars_getPos] 現在位置を取得する >>> 
 232|【引数】
 233|  ・XMLPars*  m;      XMLパーサ
 234|  ・BLex3_Pos*  pos;  現在位置
 235|************************************************************************/
 236|void  XMLPars_getPos( XMLPars* m, BLex3_Pos* pos )
 237|{
 238|  BLex3_Pos_copy( pos, &m->lineCnt.prevPos );
 239|}
 240| 
 241|/***********************************************************************
 242|  2-9. <<< [XMLPars_setPos1] 現在位置を移動する >>> 
 243|【引数】
 244|  ・XMLPars*  m;    XMLパーサ
 245|  ・int  pos;       現在位置
 246|************************************************************************/
 247|void  XMLPars_setPos1( XMLPars* m, int pos )
 248|{
 249|  BLex3_Pos  p;
 250|
 251|  p.sjis_type = BLex3_Ascii;
 252|  p.pos = pos;
 253|  BLex3_Pos_copy( &m->lineCnt.prevPos, &p );
 254|}
 255| 
 256|/***********************************************************************
 257|  2-10. <<< [XMLPars_getLineNum] 現在位置の行番号を返す >>> 
 258|【引数】
 259|  ・XMLPars*  m;  XMLパーサ
 260|  ・int  返り値;  現在位置の行番号(1〜)
 261|************************************************************************/
 262|int  XMLPars_getLineNum( XMLPars* m )
 263|{
 264|  return  m->lineCnt.iLine;
 265|}
 266|
 267| 
 268|/**************************************************************************
 269|  2-11. <<< [XMLPars_print] デバッグ表示する >>> 
 270|***************************************************************************/
 271|#ifndef  ERRORS_CUT_DEBUG_TOOL
 272|void  XMLPars_print( XMLPars* m, const char* title )
 273|{
 274|  Errors_printf( "%sXMLPars[%p]", title, m );
 275|  HtmlPars_print( &m->htmlPars, title );
 276|}
 277|#endif
 278|
 279|
 280| 
 281|