C:\home\SVGCats_src\src\Filefind.c
1|/************************************************************************** 2| 1. <<< ファイル列挙 (FileFind) >>> 3|【役割】 4|・カレントフォルダにあるファイル名を列挙します。 5|【補足】 6|・フォルダをネストして列挙する場合、NestFind クラスを用います。 7|・VC++ 1.5 では使えません。 8|***************************************************************************/ 9| 10|#ifdef USES_MXP_AUTOINC 11| #include "filefind.ah" /* Auto include header, Look at mixer-... folder */ 12|#else 13| #include "all.h" 14|#endif 15|#ifndef USES_STRX 16|#error need STRX 17|#endif 18| 19|#include <string.h> 20|#ifdef _UNIX 21| #include <stdlib.h> 22| static char CmdLine[256]; 23| static char FileName[256]; 24| #define BatName "~files_sub.bat" /* 内部で実行するバッチファイル名 */ 25| #define OutName "~files_out.txt" /*バッチファイルで出力されるファイル名*/ 26| #define TmpName "~nil.txt"/*エラーメッセージ消去用・テンポラリファイル名*/ 27|#endif 28| 29| 30| 31|/************************************************************************** 32| 2. <<< [FileFind_init] 列挙するパスを設定して初期化する >>> 33|【引数】 34| ・const char* path; 列挙するファイルを含むフォルダのパス 35|【補足】 36|・初期化しただけでは、FileFind_getFName 関数などを用いてファイル情報を 37| 参照することは出来ません。FileFind_next 関数を呼んでください。 38|***************************************************************************/ 39|#ifdef _K_AND_R 40| void FileFind_init( m, path ) 41| FileFind* m; 42| char* path; 43|#else 44| void FileFind_init( FileFind* m, const char* path ) 45|#endif 46|{ 47| #ifdef _MSC_VER 48| static char path2[256]; 49| 50| strcpy( path2, path ); 51| StrX_setLast( path2, '\\' ); 52| strcat( path2, "*.*" ); 53| m->handle = _findfirst( path2, &m->data ); 54| m->bFirst = true; 55| #endif /* _MSC_VER */ 56| /*-----------------------------------------------------*/ 57| #ifdef _UNIX 58| FILE* fbat; 59| 60| /* オブジェクトの初期化 */ 61| *m->FileName = 0; 62| m->file = NULL; /* 後で open する */ 63| 64| /* ファイル名一覧ファイルの作成 */ 65| sprintf( FileName, "%s.%p", BatName, m ); 66| fbat = fopen( FileName, "wt" ); 67| 68| if ( fbat == NULL ) { 69| fprintf( stderr, "Can't create script file in FileFind_New()." ); 70| exit(1); 71| } 72| 73| fprintf( fbat, "%s%s%s.%p%s%s%s%s%s%s%s%s%s.%p%s%s%s%s.%p%s%s%s%s%s%s", 74| "#csh\n", 75| "rm ", OutName, m, " >& ", TmpName, "\n", 76| "foreach name ( ", path, " ) \n", 77| " if ( -d $name ) then \n", 78| " echo \"$name/\" >> ", OutName, m, "\n", 79| " else\n", 80| " echo \"$name\" >> ", OutName, m, "\n", 81| " endif\n", 82| "end\n", 83| "rm ", TmpName, "\n" ); 84| 85| fclose( fbat ); 86| 87| sprintf( CmdLine, "chmod +x %s.%p", BatName, m ); 88| system( CmdLine ); 89| 90| sprintf( CmdLine, "csh %s.%p", BatName, m ); 91| system( CmdLine ); 92| 93| sprintf( CmdLine, "rm %s.%p", BatName, m ); 94| system( CmdLine ); 95| 96| /*--- ファイル名一覧ファイルの open ---*/ 97| sprintf( FileName, "%s.%p", OutName, m ); 98| m->file = fopen( FileName, "rt" ); 99| 100| if ( m->file == NULL ) { 101| fprintf( stderr, "Can't open %s.%p in FileFind_New().\n", OutName, m ); 102| exit(1); 103| } 104| #endif /* _UNIX */ 105| 106| m->bCutParent = false; 107|} 108| 109| 110| 111|/************************************************************************** 112| 3. <<< [FileFind_init2] . と .. を取得しないように初期化する >>> 113|【補足】 114|・FileFind_next 関数で次のファイル名やフォルダ名を取得するとき、.(カレント)と 115| ..(親ディレクトリ)を取得しません。それ以外は、FileFind_init と同じです。 116|***************************************************************************/ 117|#ifdef _K_AND_R 118| void FileFind_init2( m, path ) 119| FileFind* m; 120| char* path; 121|#else 122| void FileFind_init2( FileFind* m, const char* path ) 123|#endif 124|{ 125| FileFind_init( m, path ); 126| m->bCutParent = true; 127|} 128| 129| 130| 131|/************************************************************************** 132| 4. <<< [FileFind_next] カレント・ファイルを次のファイルに移動する >>> 133|【引数】 134| ・返り値 : 0=次の候補はある, 1=ない 135|***************************************************************************/ 136|#ifdef _K_AND_R 137| int FileFind_next( m ) 138| FileFind* m; 139|#else 140| int FileFind_next( FileFind* m ) 141|#endif 142|{ 143| int ret; 144| 145| do { 146| 147| #ifdef _MSC_VER 148| if ( m->bFirst ) { 149| if ( m->handle == -1 ) return 1; 150| m->bFirst = false; 151| ret = 0; 152| } 153| else { 154| ret = ( _findnext( m->handle, &m->data ) == -1 ); 155| } 156| #endif /* _MSC_VER */ 157| 158| /*-----------------------------------------------------*/ 159| 160| #ifdef _UNIX 161| char* ret; 162| 163| for(;;) { 164| ret = fgets( m->FileName, 256, m->file ); 165| 166| if ( ret != NULL ) { 167| char* p; 168| 169| StrX_BS( m->FileName ); 170| /* m->FileName[ strlen( m->FileName ) - 1 ] = '\0';*/ 171| 172| if ( StrX_Last( m->FileName ) == '/' ) { 173| StrX_BS( m->FileName ); 174| m->IsDir = true; 175| } 176| else 177| m->IsDir = false; 178| 179| if ( ( p = StrX_RSearch( m->FileName, "/" ) ) != NULL ) { 180| memmove( m->FileName, p+1, strlen( p+1 ) + 1 ); 181| } 182| sprintf( FileName, "%s.%p", OutName, m ); 183| if ( strncmp( m->FileName, OutName, strlen(OutName) ) == 0 ) 184| continue; 185| ret = 0; 186| } 187| else { 188| ret = 1; 189| } 190| } 191| #endif /* _UNIX */ 192| 193| if ( ret == 1 || ! m->bCutParent ) break; 194| } while ( strcmp( FileFind_getFName( m ), "." ) == 0 || 195| strcmp( FileFind_getFName( m ), ".." ) == 0 ); 196| 197| return ret; 198|} 199| 200| 201| 202|/************************************************************************** 203| 5. <<< [FileFind_finish] 後始末する >>> 204|***************************************************************************/ 205|#ifdef _K_AND_R 206| void FileFind_finish( m ) 207| FileFind* m; 208|#else 209| void FileFind_finish( FileFind* m ) 210|#endif 211|{ 212| #ifdef _MSC_VER 213| _findclose( m->handle ); 214| #endif /* _MSC_VER */ 215| #ifdef _UNIX 216| fclose( m->file ); 217| 218| sprintf( CmdLine, "rm %s.%p", OutName, m ); 219| system( CmdLine ); 220| #endif /* _UNIX */ 221|} 222| 223|/************************************************************************** 224| 6. <<< [FileFind_getN] フォルダに含まれるファイルやフォルダの数を返す >>> 225|【引数】 226| ・char* path; フォルダパス 227| ・bool bPlusFolder フォルダをカウントするかどうか 228| ・bool bPlusFile ファイルをカウントするかどうか 229| ・int 返り値; フォルダ数、ファイル数またはその合計 230|***************************************************************************/ 231|int FileFind_getN( const char* path, bool bPlusFolder, bool bPlusFile ) 232|{ 233| int i; 234| int handle; 235| struct _finddata_t data; 236| int flag; 237| char path2[_MAX_PATH]; 238| 239| /* data.attrib と比較する値 flag を求める */ 240| if ( bPlusFolder ) { 241| if ( bPlusFile ) flag = ~_A_SUBDIR; /* xor で必ず 非0 になる値 */ 242| else flag = 0; 243| } 244| else { 245| if ( bPlusFile ) flag = _A_SUBDIR; 246| else return 0; 247| } 248| 249| /* ワイルドカード "*.*" を含めたパス path2 を求める */ 250| strcpy( path2, path ); 251| StrX_setLast( path2, '\\' ); 252| strcat( path2, "*.*" ); 253| 254| /* ファイル数・フォルダ数をカウントする */ 255| i = 0; 256| handle = _findfirst( path2, &data ); 257| if ( handle != -1 ) { 258| do { 259| if ( ( ( data.attrib & _A_SUBDIR ) ^ flag ) != 0 && 260| strcmp( data.name, "." ) != 0 && strcmp( data.name, ".." ) != 0 ) { 261| i++; 262| } 263| } while ( _findnext( handle, &data ) != -1 ); 264| } 265| _findclose( handle ); 266| 267| return i; 268|} 269| 270|