グローバル関数 ローカル関数
mssCpyOptKey
mssFreeOption
mssHelpDoc
mssIsFldOptOn
mssIsInRange
mssSetOption
mssShowOption
chkMust
getNextStr
prnComHlp
prnComXml
prnMan
0001: /**
0002: * # CHAPTER #
0003: * ============================================================================
0004: * MUSASHIで用いられるオプション関連の関数
0005: * ============================================================================
0006: */
0007:
0008: #include <mssOption.h>
0009: #include <mssBase.h>
0010: #include <mssXml.h>
0011:
0012: #include <stdio.h>
0013: #include <stdlib.h>
0014: #include <string.h>
0015: #include <sys/time.h>
0016: #include <unistd.h>
0017: #include <float.h>
0018: #include <limits.h>
0019: #include <glob.h>
0020:
0021: extern struct mssGlobalVariables mssGV;
0022:
0023: /**
0024: * # FUNCTION #
0025: * 文字列リストstrListのcnt個の各文字列について、一つ目に出現するトークン(tok)
0026: * で分割し、その後の文字列リストを返す。
0027: *
0028: * ex.)
0029: * strList={"aaa:bbb","ccc:ddd","eee:fff"}
0030: * ->
0031: * strList={"aaa","ccc","eee"} 返値={"bbb","ddd","fff"}
0032: */
0033: static char **getNextStr(char **strList, int cnt, char tok)
0034: {
0035: char *colPos;
0036: char **list=NULL;
0037: int i;
0038:
0039: if(strList==NULL) return(NULL);
0040:
0041: list=mssMalloc(sizeof(char *)*cnt,"tokCol");
0042: for(i=0; i<cnt; i++){
0043: if( *(strList+i)!=NULL ){
0044: colPos=strchr(*(strList+i),tok);
0045: if(colPos!=NULL){
0046: *colPos='\0';
0047: *(list+i)=++colPos;
0048: }else{
0049: *(list+i)=NULL;
0050: }
0051: }else{
0052: *(list+i)=NULL;
0053: }
0054: }
0055: return(list);
0056: }
0057:
0058: /**
0059: * # FUNCTION #
0060: * 各種オプションの構造体の領域を開放する。
0061: * 異るオプションの構造体をvoidポインタで与え、第一要素のタイプで判断して
0062: * 各オプションに応じた開放を実現している。
0063: */
0064: void mssFreeOption(void *opt[])
0065: {
0066: int i,j;
0067:
0068: MssOptSTR *optSTR;
0069: MssOptSEL *optSEL;
0070: MssOptSLS *optSLS;
0071: MssOptINT *optINT;
0072: MssOptILS *optILS;
0073: MssOptRNG *optRNG;
0074: MssOptDBL *optDBL;
0075: MssOptDLS *optDLS;
0076: MssOptFLD *optFLD;
0077: MssOptKEY *optKEY;
0078: MssOptINF *optINF;
0079: MssOptOTF *optOTF;
0080:
0081: i=0;
0082: while(opt[i]!=NULL){
0083: switch( ((MssOptKEY *)opt[i])->type ){
0084: case OSTR:
0085: optSTR=(MssOptSTR *)opt[i];
0086: mssFree(optSTR->str);
0087: break;
0088:
0089: case OSEL:
0090: optSEL=(MssOptSEL *)opt[i];
0091: mssFree(optSEL->str);
0092: break;
0093:
0094: case OSLS:
0095: optSLS=(MssOptSLS *)opt[i];
0096: mssFree(optSLS->str );
0097: if(optSLS->strList!=NULL){
0098: mssFree(*optSLS->strList);
0099: }
0100: mssFree(optSLS->strList);
0101: mssFree(optSLS->colList);
0102: break;
0103:
0104: case OINT:
0105: optINT=(MssOptINT *)opt[i];
0106: mssFree(optINT->str );
0107: break;
0108:
0109: case OILS:
0110: optILS=(MssOptILS *)opt[i];
0111: mssFree(optILS->str );
0112: mssFree(optILS->val );
0113: break;
0114:
0115: case ORNG:
0116: optRNG=(MssOptRNG *)opt[i];
0117: mssFree(optRNG->str );
0118: mssFree(optRNG->from);
0119: mssFree(optRNG->to );
0120: break;
0121:
0122: case ODBL:
0123: optDBL=(MssOptDBL *)opt[i];
0124: mssFree(optDBL->str);
0125: break;
0126:
0127: case ODLS:
0128: optDLS=(MssOptDLS *)opt[i];
0129: mssFree(optDLS->str );
0130: mssFree(optDLS->val );
0131: break;
0132:
0133: case OFLD:
0134: optFLD=(MssOptFLD *)opt[i];
0135: mssFree(optFLD->str);
0136: if(optFLD->nam!=NULL){
0137: mssFree(*optFLD->nam);
0138: }
0139: mssFree(optFLD->nam );
0140: mssFree(optFLD->newNam);
0141: mssFree(optFLD->fldOpt);
0142: break;
0143:
0144: case OKEY:
0145: optKEY=(MssOptKEY *)opt[i];
0146: mssFree(optKEY->str);
0147: if(optKEY->nam!=NULL){
0148: mssFree(*optKEY->nam);
0149: }
0150: mssFree(optKEY->nam );
0151: break;
0152:
0153: case OINF:
0154: optINF=(MssOptINF *)opt[i];
0155: mssFree(optINF->str);
0156: if(optINF->strList!=NULL){
0157: for(j=0; j<optINF->cnt; j++){
0158: mssFree(*(optINF->strList+j));
0159: }
0160: mssFree(optINF->strList);
0161: }
0162: break;
0163:
0164: case OOTF:
0165: optOTF=(MssOptOTF *)opt[i];
0166: mssFree(optOTF->str);
0167: break;
0168:
0169: case OFLG:
0170: break;
0171: }
0172: i++;
0173: }
0174: }
0175:
0176: /**
0177: * # FUNCTION #
0178: * オプション構造体のsetフラグとmustフラグから、必須指定パラメータが
0179: * 指定されているかどうかチェックする。
0180: * 指定されていなければ、エラーメッセージを出力して終了する。
0181: * xmlTableの場合は、must==1 && set!=1でエラー(必須指定パラメータなし)となる。
0182: * plain textの場合は、xmlTableの場合の条件に加えて、
0183: * must==2 && set==1でもエラー(そのパラメータは必要ない)となる。
0184: */
0185: static void chkMust(char *keyWord, int set, int must)
0186: {
0187:
0188: if(!mssGV.txtFlg){
0189: if(!set && must){
0190: mssShowErrMsg("option -%s is mandatory",keyWord);
0191: exit(mssErrorNoDefault);
0192: }
0193: }else{
0194: if(set && must==2){
0195: mssShowErrMsg("option -%s is not needed with -t option",keyWord);
0196: exit(mssErrorNoDefault);
0197: }
0198: if(!set && must==1){
0199: mssShowErrMsg("option -%s is mandatory",keyWord);
0200: exit(mssErrorNoDefault);
0201: }
0202: }
0203: }
0204:
0205: /**
0206: * # FUNCTION #
0207: * コマンド側で定義した複数のオプション構造体(opt[])の未定義メンバー変数
0208: * をコマンドライン引数を用いて設定する。
0209: * ただし、コマンドライン引数のうち、以下のパラメータ指定シンボルは特殊な意味
0210: * として解釈される。
0211: * -Q : 終了メッセージを表示しない。
0212: * -t : xmlTableでなく、plainTextを入出力データとして用いる。
0213: * また、通常mssHelpDoc関数を呼び出すことにより-h,-x,-Xも特殊な意味として解釈
0214: * される。
0215: */
0216: void mssSetOption(void *opt[], int argc, char *argv[])
0217: {
0218: int optCnt=-1;
0219: enum OptType *optType;
0220: char *optLst;
0221: int i,j;
0222: int c;
0223: int err;
0224: int len;
0225: char **list1;
0226: char **list2;
0227: int cnt;
0228: glob_t fname;
0229:
0230: MssOptSTR *optSTR;
0231: MssOptSEL *optSEL;
0232: MssOptSLS *optSLS;
0233: MssOptINT *optINT;
0234: MssOptILS *optILS;
0235: MssOptRNG *optRNG;
0236: MssOptDBL *optDBL;
0237: MssOptDLS *optDLS;
0238: MssOptFLD *optFLD;
0239: MssOptKEY *optKEY;
0240: MssOptINF *optINF;
0241: MssOptOTF *optOTF;
0242: MssOptFLG *optFLG;
0243:
0244: /* -tが指定されていればmssGV.txtFlgをonにする */
0245: for(i=1; i<argc; i++) if(*argv[i]=='-' && *(argv[i]+1)=='t') mssGV.txtFlg=1;
0246:
0247: /* getopt関数にエラーメッセージを出力させない */
0248: opterr=0;
0249:
0250: /* オプションの数をカウントする */
0251: while( opt[++optCnt]!=NULL );
0252:
0253: /* 各オプション毎の型をoptTypeにセットする */
0254: optType=mssMalloc(sizeof(enum OptType)*optCnt,"setOption");
0255: for(i=0; i<optCnt; i++){
0256: /*最初のtypeまでは構造が同じなのでMssOptKEYを代表して使う*/
0257: *(optType+i)=((MssOptKEY *)opt[i])->type;
0258: }
0259:
0260: /* getopt用のオプションリストを作成する */
0261: /* -k key -f fld -n -z -> ":k:f:nz" */
0262: optLst=mssMalloc(sizeof(char)*optCnt*2+3,"setOption");
0263: /* 最初が:ということは、引数が必要なオプションで引数がなければ */
0264: /* '?'のかわりに':'を返すことになる。 */
0265: strcpy(optLst,":");
0266: for(i=0; i<optCnt; i++){
0267: if( *(optType+i)==OFLG ){ /*引数を伴わないオプション*/
0268: strcat(optLst,((MssOptKEY *)opt[i])->keyWord);
0269: }else{ /*引数を伴うオプション*/
0270: strcat(optLst,((MssOptKEY *)opt[i])->keyWord);
0271: strcat(optLst,":");
0272: }
0273: }
0274: strcat(optLst,"Q");
0275: mssFree(optType);
0276:
0277: /*コマンドライン指定フラグの初期化*/
0278: for(i=0; i<optCnt; i++){
0279: switch( ((MssOptKEY *)opt[i])->type ){
0280: case OSTR: ((MssOptSTR *)opt[i])->set=0; break;
0281: case OSEL: ((MssOptSEL *)opt[i])->set=0; break;
0282: case OSLS: ((MssOptSLS *)opt[i])->set=0; break;
0283: case OINT: ((MssOptINT *)opt[i])->set=0; break;
0284: case OILS: ((MssOptILS *)opt[i])->set=0; break;
0285: case ORNG: ((MssOptRNG *)opt[i])->set=0; break;
0286: case ODBL: ((MssOptDBL *)opt[i])->set=0; break;
0287: case ODLS: ((MssOptDLS *)opt[i])->set=0; break;
0288: case OFLD: ((MssOptFLD *)opt[i])->set=0; break;
0289: case OKEY: ((MssOptKEY *)opt[i])->set=0; break;
0290: case OINF: ((MssOptINF *)opt[i])->set=0; break;
0291: case OOTF: ((MssOptOTF *)opt[i])->set=0; break;
0292: case OFLG: ((MssOptFLG *)opt[i])->set=0; break;
0293: }
0294: }
0295:
0296: /* getoptでオプションをセットする */
0297: while(1){
0298: c=getopt(argc,argv, optLst);
0299: if(c==-1) break;
0300:
0301: if(c==':'){
0302: mssShowErrMsg("option -%c needs a value",optopt);
0303: exit(mssErrorNoDefault);
0304: }
0305:
0306: if(c=='?'){
0307: mssShowErrMsg("unknown option: -%c",optopt);
0308: exit(mssErrorNoDefault);
0309: }
0310:
0311: if(c=='Q'){ /* メッセージ表示無しモード*/
0312: mssGV.quiet=1;
0313: continue;
0314: }
0315:
0316: /*コマンドライン指定フラグ(set)とパラメータ文字のセット(str)*/
0317: for(i=0; i<optCnt; i++){
0318: if( c == *((MssOptKEY *)opt[i])->keyWord ){
0319: switch( ((MssOptKEY *)opt[i])->type ){
0320: case OSTR:
0321: optSTR=(MssOptSTR *)opt[i];
0322: optSTR->set=1;
0323: optSTR->str=mssStrdup(optarg);
0324: break;
0325: case OSEL:
0326: optSEL=(MssOptSEL *)opt[i];
0327: optSEL->set=1;
0328: optSEL->str=mssStrdup(optarg);
0329: break;
0330: case OSLS:
0331: optSLS=(MssOptSLS *)opt[i];
0332: optSLS->set=1;
0333: optSLS->str=mssStrdup(optarg);
0334: break;
0335: case OINT:
0336: optINT=(MssOptINT *)opt[i];
0337: optINT->set=1;
0338: optINT->str=mssStrdup(optarg);
0339: break;
0340: case OILS:
0341: optILS=(MssOptILS *)opt[i];
0342: optILS->set=1;
0343: optILS->str=mssStrdup(optarg);
0344: break;
0345: case ORNG:
0346: optRNG=(MssOptRNG *)opt[i];
0347: optRNG->set=1;
0348: optRNG->str=mssStrdup(optarg);
0349: break;
0350: case ODBL:
0351: optDBL=(MssOptDBL *)opt[i];
0352: optDBL->set=1;
0353: optDBL->str=mssStrdup(optarg);
0354: break;
0355: case ODLS:
0356: optDLS=(MssOptDLS *)opt[i];
0357: optDLS->set=1;
0358: optDLS->str=mssStrdup(optarg);
0359: break;
0360: case OFLD:
0361: optFLD=(MssOptFLD *)opt[i];
0362: optFLD->set=1;
0363: optFLD->str=mssStrdup(optarg);
0364: break;
0365: case OKEY:
0366: optKEY=(MssOptKEY *)opt[i];
0367: optKEY->set=1;
0368: optKEY->str=mssStrdup(optarg);
0369: break;
0370: case OINF:
0371: optINF=(MssOptINF *)opt[i];
0372: optINF->set=1;
0373: optINF->str=mssStrdup(optarg);
0374: break;
0375: case OOTF:
0376: optOTF=(MssOptOTF *)opt[i];
0377: optOTF->set=1;
0378: optOTF->str=mssStrdup(optarg);
0379: break;
0380: case OFLG:
0381: optFLG=(MssOptFLG *)opt[i];
0382: optFLG->set=1;
0383: break;
0384: }
0385: }
0386: }
0387: }
0388: mssFree(optLst);
0389:
0390: /* 1: mustによるチェック */
0391: /* 2: 指定のなかったオプションについてデフォルト値をstrにセット */
0392: /* MssOptINF,MssOptOTF,MssOptFLDはデフォルトなしなのでNULLをセット */
0393: /* MssOptKEYはdefが1or2をとるが、strにはNULLをセット。 */
0394: /* MssOptFLGはdefをsetとしてセットする。 */
0395: /* 3: 各型に応じて、strの内容を解析し、各種変数にセットする */
0396: err=0;
0397: for(i=0; i<optCnt; i++){
0398: switch( ((MssOptKEY *)opt[i])->type ){
0399: case OSTR:
0400: optSTR=(MssOptSTR *)opt[i];
0401: chkMust(optSTR->keyWord,optSTR->set,optSTR->must);
0402: if(!optSTR->set && optSTR->def!=NULL) optSTR->str=mssStrdup(optSTR->def);
0403:
0404: /*チェック*/
0405: if(optSTR->set){
0406: len=strlen(optSTR->str);
0407: if(len<optSTR->minLen || len >optSTR->maxLen){
0408: mssShowErrMsg("length of option value is out of range : -%s %s (%d,%d)", optSTR->keyWord,optSTR->str,optSTR->minLen,optSTR->maxLen);
0409: exit(mssErrorNoDefault);
0410: }
0411: }
0412: break;
0413:
0414: case OSEL:
0415: optSEL=(MssOptSEL *)opt[i];
0416: chkMust(optSEL->keyWord,optSEL->set,optSEL->must);
0417: if(!optSEL->set && optSEL->def!=NULL) optSEL->str=mssStrdup(optSEL->def);
0418:
0419: /*チェック*/
0420: if(optSEL->set){
0421: cnt=0;
0422: list1=mssTokByChr(optSEL->selList,',',&cnt,1);
0423: for(j=0;j<cnt;j++){
0424: if(0==strcmp(*(list1+j),optSEL->str)) break;
0425: }
0426: if(j==cnt) {
0427: mssShowErrMsg("argument must be one of \"%s\" on option -%s",optSEL->selList,optSEL->keyWord);
0428: exit(mssErrorNoDefault);
0429: }
0430: mssFree(*list1);
0431: mssFree(list1);
0432: }
0433: break;
0434:
0435: case OSLS:
0436: optSLS=(MssOptSLS *)opt[i];
0437: chkMust(optSLS->keyWord,optSLS->set,optSLS->must);
0438: if(!optSLS->set && optSLS->def!=NULL) optSLS->str=mssStrdup(optSLS->def);
0439:
0440: /*初期化*/
0441: optSLS->strList=NULL;
0442: optSLS->colList=NULL;
0443: optSLS->cnt=0;
0444:
0445: /*strがNULLならリターン*/
0446: if( optSLS->str==NULL ) break;
0447:
0448: /*カンマによるトークン分割*/
0449: optSLS->strList=mssTokByChr(optSLS->str,',',&optSLS->cnt,1);
0450:
0451: /*コロンによるトークン分割*/
0452: optSLS->colList=getNextStr(optSLS->strList,optSLS->cnt,':');
0453:
0454: /*チェック*/
0455: if(optSLS->set){
0456: if(optSLS->cnt>optSLS->maxCnt){
0457: mssShowErrMsg("the max number of elements in the option is %d: -%s %s", optSLS->maxCnt,optSLS->keyWord,optSLS->str);
0458: exit(mssErrorNoDefault);
0459: }
0460: for(j=0; j<optSLS->cnt; j++){
0461: if(*(optSLS->strList+j)==NULL || **(optSLS->strList+j)=='\0')
0462: len=0;
0463: else
0464: len=strlen(*(optSLS->strList+j));
0465: if(len<optSLS->minLen || len >optSLS->maxLen){
0466: mssShowErrMsg("length of %dth element of the option is out of range : -%s %s (%d,%d)", j+1,optSLS->keyWord,optSLS->str,optSLS->minLen,optSLS->maxLen);
0467: exit(mssErrorNoDefault);
0468: }
0469: }
0470: if(!optSLS->colFlg){
0471: for(j=0; j<optSLS->cnt; j++){
0472: if(*(optSLS->colList+j)!=NULL){
0473: mssShowErrMsg("can not use ':' in the %dth element : -%s %s)",
0474: j+1,optSLS->keyWord,optSLS->str);
0475: exit(mssErrorNoDefault);
0476: }
0477: }
0478: }
0479: }
0480: break;
0481:
0482: case OINT:
0483: optINT=(MssOptINT *)opt[i];
0484: chkMust(optINT->keyWord,optINT->set,optINT->must);
0485: if(!optINT->set){
0486: optINT->str=NULL;
0487: optINT->val=optINT->def;
0488: }else{
0489: optINT->val=atoi(optINT->str);
0490: }
0491:
0492: /*チェック*/
0493: if(optINT->min>optINT->val || optINT->max<optINT->val){
0494: mssShowErrMsg("the value of option -%s is out of range : %d(%d,%d)",
0495: optINT->keyWord,optINT->val,optINT->min,optINT->max);
0496: exit(mssErrorNoDefault);
0497: }
0498: break;
0499:
0500: case OILS:
0501: optILS=(MssOptILS *)opt[i];
0502: chkMust(optILS->keyWord,optILS->set,optILS->must);
0503: if(!optILS->set && optILS->def!=NULL) optILS->str=mssStrdup(optILS->def);
0504:
0505: /*初期化*/
0506: optILS->val=NULL;
0507: optILS->cnt=0;
0508:
0509: /*strがNULLならリターン*/
0510: if( optILS->str==NULL ) break;
0511:
0512: /*カンマによるトークン分割*/
0513: list1=mssTokByChr(optILS->str,',',&optILS->cnt,1);
0514:
0515: /*list1の文字列を数値リストに変換*/
0516: optILS->val=mssMalloc(sizeof(int)*optILS->cnt,"option");
0517: for(j=0; j<optILS->cnt; j++){
0518: if(0==strcmp(*(list1+j),"MIN")){
0519: *(optILS->val+j)=optILS->min;
0520: }else if(0==strcmp(*(list1+j),"MAX")){
0521: *(optILS->val+j)=optILS->max;
0522: }else{
0523: *(optILS->val+j)=atoi(*(list1+j));
0524: }
0525: }
0526:
0527: /*チェック*/
0528: if(optILS->set){
0529: if(optILS->cnt>optILS->maxCnt){
0530: mssShowErrMsg("the max number of elements in the option is %d: -%s %s", optILS->maxCnt,optILS->keyWord,optILS->str);
0531: exit(mssErrorNoDefault);
0532: }
0533: for(j=0; j<optILS->cnt; j++){
0534: if(*(list1+j)==NULL || **(list1+j)=='\0'){
0535: mssShowErrMsg("%dth element is empty : -%s %s",
0536: j+1,optILS->keyWord,optILS->str);
0537: exit(mssErrorNoDefault);
0538: }
0539: }
0540: for(j=0; j<optILS->cnt; j++){
0541: if(*(optILS->val+j)<optILS->min || *(optILS->val+j)>optILS->max ){
0542: mssShowErrMsg("%dth element value is out of range : -%s %s (%d,%d)", j+1,optILS->keyWord,optILS->str,optILS->min,optILS->max);
0543: exit(mssErrorNoDefault);
0544: }
0545: }
0546: }
0547: mssFree(*list1);
0548: mssFree(list1);
0549: break;
0550:
0551: case ORNG:
0552: optRNG=(MssOptRNG *)opt[i];
0553: chkMust(optRNG->keyWord,optRNG->set,optRNG->must);
0554: if(!optRNG->set && optRNG->def!=NULL) optRNG->str=mssStrdup(optRNG->def);
0555:
0556: /*初期化*/
0557: optRNG->from=NULL;
0558: optRNG->to =NULL;
0559: optRNG->cnt =0;
0560:
0561: /*strがNULLならリターン*/
0562: if( optRNG->str==NULL ) break;
0563:
0564: /*カンマによるトークン分割*/
0565: list1=mssTokByChr(optRNG->str,',',&optRNG->cnt,1);
0566:
0567: /*アンダーバーによるトークン分割*/
0568: list2=getNextStr(list1,optRNG->cnt,'_');
0569:
0570: /*list1,list2の文字列を数値範囲に変換*/
0571: optRNG->from=mssMalloc(sizeof(int)*optRNG->cnt,"option");
0572: optRNG->to =mssMalloc(sizeof(int)*optRNG->cnt,"option");
0573: for(j=0; j<optRNG->cnt; j++){
0574: if(0==strcmp(*(list1+j),"MIN")){
0575: *(optRNG->from+j)=optRNG->min;
0576: }else if(0==strcmp(*(list1+j),"MAX")){
0577: *(optRNG->from+j)=optRNG->max;
0578: }else{
0579: *(optRNG->from+j)=atoi(*(list1+j));
0580: }
0581: if(*(list2+j) == NULL){
0582: *(optRNG->to+j)=*(optRNG->from+j);
0583: }else if(0==strcmp(*(list2+j),"MIN")){
0584: *(optRNG->to+j)=optRNG->min;
0585: }else if(0==strcmp(*(list2+j),"MAX")){
0586: *(optRNG->to+j)=optRNG->max;
0587: }else{
0588: *(optRNG->to+j)=atoi(*(list2+j));
0589: }
0590: }
0591:
0592: /*チェック*/
0593: if(optRNG->set){
0594: if(optRNG->cnt>optRNG->maxCnt){
0595: mssShowErrMsg("the max number of elements in the option is %d: -%s %s", optRNG->maxCnt,optRNG->keyWord,optRNG->str);
0596: exit(mssErrorNoDefault);
0597: }
0598: for(j=0; j<optRNG->cnt; j++){
0599: if(*(list1+j)==NULL || **(list1+j)=='\0'){
0600: mssShowErrMsg("%dth element is empty : -%s %s",
0601: j+1,optRNG->keyWord,optRNG->str);
0602: exit(mssErrorNoDefault);
0603: }
0604: }
0605: for(j=0; j<optRNG->cnt; j++){
0606: if(*(optRNG->from+j)<optRNG->min || *(optRNG->to+j)>optRNG->max ||
0607: *(optRNG->from+j)>optRNG->max || *(optRNG->to+j)<optRNG->min ){
0608: mssShowErrMsg("%dth element value is out of range : -%s %s (%d,%d)", j+1,optRNG->keyWord,optRNG->str,optRNG->min,optRNG->max);
0609: exit(mssErrorNoDefault);
0610: }
0611: }
0612: }
0613:
0614: mssFree(*list1);
0615: mssFree(list1);
0616: mssFree(list2);
0617: break;
0618:
0619: case ODBL:
0620: optDBL=(MssOptDBL *)opt[i];
0621: chkMust(optDBL->keyWord,optDBL->set,optDBL->must);
0622: if(!optDBL->set){
0623: optDBL->str=NULL;
0624: optDBL->val=optDBL->def;
0625: }else{
0626: optDBL->val=atof(optDBL->str);
0627: }
0628:
0629: /*チェック*/
0630: if(optDBL->min>optDBL->val || optDBL->max<optDBL->val){
0631: mssShowErrMsg("the value of option -%s is out of range : %g(%g,%g)",
0632: optDBL->keyWord,optDBL->val,optDBL->min,optDBL->max);
0633: exit(mssErrorNoDefault);
0634: }
0635: break;
0636:
0637: case ODLS:
0638: optDLS=(MssOptDLS *)opt[i];
0639: chkMust(optDLS->keyWord,optDLS->set,optDLS->must);
0640: if(!optDLS->set && optDLS->def!=NULL) optDLS->str=mssStrdup(optDLS->def);
0641:
0642: /*初期化*/
0643: optDLS->val=NULL;
0644: optDLS->cnt=0;
0645:
0646: /*strがNULLならリターン*/
0647: if( optDLS->str==NULL ) break;
0648:
0649: /*カンマによるトークン分割*/
0650: list1=mssTokByChr(optDLS->str,',',&optDLS->cnt,1);
0651:
0652: /*list1の文字列を数値リストに変換*/
0653: optDLS->val=mssMalloc(sizeof(double)*optDLS->cnt,"option");
0654: for(j=0; j<optDLS->cnt; j++){
0655: if(0==strcmp(*(list1+j),"MIN")){
0656: *(optDLS->val+j)=optDLS->min;
0657: }else if(0==strcmp(*(list1+j),"MAX")){
0658: *(optDLS->val+j)=optDLS->max;
0659: }else{
0660: *(optDLS->val+j)=atof(*(list1+j));
0661: }
0662: }
0663:
0664: /*チェック*/
0665: if(optDLS->set){
0666: if(optDLS->cnt>optDLS->maxCnt){
0667: mssShowErrMsg("the max number of elements in the option is %d: -%s %s", optDLS->maxCnt,optDLS->keyWord,optDLS->str);
0668: exit(mssErrorNoDefault);
0669: }
0670: for(j=0; j<optDLS->cnt; j++){
0671: if(*(list1+j)==NULL || **(list1+j)=='\0'){
0672: mssShowErrMsg("%dth element is empty : -%s %s",
0673: j+1,optDLS->keyWord,optDLS->str);
0674: exit(mssErrorNoDefault);
0675: }
0676: }
0677: for(j=0; j<optDLS->cnt; j++){
0678: if(*(optDLS->val+j)<optDLS->min || *(optDLS->val+j)>optDLS->max ){
0679: mssShowErrMsg("%dth element value is out of range : -%s %s (%g,%g)", j+1,optDLS->keyWord,optDLS->str,optDLS->min,optDLS->max);
0680: exit(mssErrorNoDefault);
0681: }
0682: }
0683: }
0684: mssFree(*list1);
0685: mssFree(list1);
0686: break;
0687:
0688: case OFLD:
0689: optFLD=(MssOptFLD *)opt[i];
0690: chkMust(optFLD->keyWord,optFLD->set,optFLD->must);
0691: if(!optFLD->set) optFLD->str=NULL;
0692:
0693: /*初期化*/
0694: optFLD=(MssOptFLD *)opt[i];
0695: optFLD->nam=NULL;
0696: optFLD->newNam=NULL;
0697: optFLD->fldOpt=NULL;
0698: optFLD->cnt=0;
0699:
0700: /*strがNULLならリターン*/
0701: if( optFLD->str==NULL ) break;
0702:
0703: /*カンマによるトークン分割*/
0704: optFLD->nam=mssTokByChr(optFLD->str,',',&optFLD->cnt,1);
0705:
0706: /*:によるトークン分割*/
0707: optFLD->newNam=getNextStr(optFLD->nam,optFLD->cnt,':');
0708:
0709: /*%によるトークン分割*/
0710: optFLD->fldOpt=getNextStr(optFLD->nam,optFLD->cnt,'%');
0711:
0712: /*チェック*/
0713: /*maxCntを超えていればエラー*/
0714: if(optFLD->set){
0715: if(optFLD->cnt>optFLD->maxCnt){
0716: mssShowErrMsg("the max number of fields in the option is %d: -%s %s", optFLD->maxCnt,optFLD->keyWord,optFLD->str);
0717: exit(mssErrorNoDefault);
0718: }
0719: }
0720: /*新項目名が指定できないのに指定していればエラー*/
0721: if(!optFLD->newFlg){
0722: for(j=0; j<optFLD->cnt; j++){
0723: if(*(optFLD->newNam+j)!=NULL){
0724: mssShowErrMsg("can't use new field name : -%s %s",optFLD->keyWord,optFLD->str);
0725: exit(mssErrorNoDefault);
0726: }
0727: }
0728: }
0729: break;
0730:
0731: case OKEY:
0732: optKEY=(MssOptKEY *)opt[i];
0733: chkMust(optKEY->keyWord,optKEY->set,optKEY->must);
0734: if(!optKEY->set) optKEY->str=NULL;
0735:
0736: /*初期化*/
0737: optKEY=(MssOptKEY *)opt[i];
0738: optKEY->nam=NULL;
0739: optKEY->diffSame=0;
0740: optKEY->cnt=0;
0741:
0742: /*strがNULLならdiffSameをdefからセットしてリターン*/
0743: if( optKEY->str==NULL ){
0744: optKEY->diffSame=optKEY->def;
0745: break;
0746:
0747: /*strが#diff#,#same#ならそれぞれ1,2をセット */
0748: /* set=0,str=NULL すなわち-kで指定しなかったこととする */
0749: }else{
0750: if( 0==strcmp(optKEY->str,"#diff#") ){
0751: optKEY->diffSame=1;
0752: optKEY->set=0;
0753: mssFree(optKEY->str);
0754: optKEY->str=NULL;
0755: break;
0756: }
0757: if( 0==strcmp(optKEY->str,"#same#") ){
0758: optKEY->diffSame=2;
0759: optKEY->set=0;
0760: mssFree(optKEY->str);
0761: optKEY->str=NULL;
0762: break;
0763: }
0764: }
0765:
0766: /*カンマによるトークン分割*/
0767: optKEY->nam=mssTokByChr(optKEY->str,',',&optKEY->cnt,1);
0768:
0769: /*チェック*/
0770: if(optKEY->set){
0771: if(optKEY->cnt>optKEY->maxCnt){
0772: mssShowErrMsg("the max number of fields in the option is %d: -%s %s", optKEY->maxCnt,optKEY->keyWord,optKEY->str);
0773: exit(mssErrorNoDefault);
0774: }
0775: }
0776: break;
0777:
0778: case OINF:
0779: optINF=(MssOptINF *)opt[i];
0780: chkMust(optINF->keyWord,optINF->set,optINF->must);
0781: if(!optINF->set) optINF->str=NULL;
0782:
0783: /*初期化*/
0784: optINF->strList=NULL;
0785: optINF->cnt=0;
0786:
0787: /*strがNULLならリターン*/
0788: if(optINF->str==NULL) break;
0789:
0790: /*カンマによるトークン分割*/
0791: optINF->strList=mssTokByChr(optINF->str,',',&optINF->cnt,1);
0792:
0793: /*チェック*/
0794: if(optINF->set){
0795: if(optINF->cnt>optINF->maxCnt){
0796: mssShowErrMsg("the max number of elements in the option is %d: -%s %s", optINF->maxCnt,optINF->keyWord,optINF->str);
0797: exit(mssErrorNoDefault);
0798: }
0799: }
0800:
0801: /*ワイルドカードの展開*/
0802: fname.gl_pathc=0;
0803: for(j=0; j<optINF->cnt; j++){
0804: if(fname.gl_pathc==0){
0805: glob(*(optINF->strList+j),0, NULL, &fname);
0806: }else{
0807: glob(*(optINF->strList+j),GLOB_APPEND, NULL, &fname);
0808: }
0809: }
0810:
0811: mssFree(*optINF->strList);
0812: mssFree(optINF->strList);
0813: optINF->cnt=fname.gl_pathc;
0814: if(optINF->cnt!=0){
0815: optINF->strList=mssMalloc(sizeof(char *)*optINF->cnt,"option");
0816: for(j=0; j<optINF->cnt; j++){
0817: *(optINF->strList+j)=mssStrdup(*(fname.gl_pathv+j));
0818: }
0819: }else{
0820: optINF->strList=NULL;
0821: if(!optINF->fnf) {
0822: mssShowErrMsg("file not found : -%s %s",optINF->keyWord,optINF->str);
0823: exit(mssErrorNoDefault);
0824: }
0825: }
0826: globfree(&fname);
0827: break;
0828:
0829: case OOTF:
0830: optOTF=(MssOptOTF *)opt[i];
0831: chkMust(optOTF->keyWord,optOTF->set,optOTF->must);
0832: if(!optOTF->set) optOTF->str=NULL;
0833: break;
0834:
0835: case OFLG:
0836: optFLG=(MssOptFLG *)opt[i];
0837: if(!optFLG->set) optFLG->set=optFLG->def;
0838: break;
0839: }
0840: }
0841: }
0842:
0843: /**
0844: * # FUNCTION #
0845: * オプション構造体の内容を表示する(debug用)。
0846: */
0847: void mssShowOption(void *opt[])
0848: {
0849: int i,j;
0850: MssOptSTR *optSTR;
0851: MssOptSEL *optSEL;
0852: MssOptSLS *optSLS;
0853: MssOptINT *optINT;
0854: MssOptILS *optILS;
0855: MssOptRNG *optRNG;
0856: MssOptDBL *optDBL;
0857: MssOptDLS *optDLS;
0858: MssOptFLD *optFLD;
0859: MssOptKEY *optKEY;
0860: MssOptINF *optINF;
0861: MssOptOTF *optOTF;
0862: MssOptFLG *optFLG;
0863:
0864: i=0;
0865: while(opt[i]!=NULL){
0866: fprintf(stderr,"option=%s ",((MssOptSLS *)opt[i])->keyWord);
0867:
0868: switch( ((MssOptKEY *)opt[i])->type ){
0869: case OSTR:
0870: optSTR=(MssOptSTR *)opt[i];
0871: fprintf(stderr,"(STR) ");
0872: /* ####### set */
0873: if( optSTR->set ) fprintf(stderr,"--> set in command line\n");
0874: else fprintf(stderr,"--> not set in command line\n");
0875:
0876: /* ####### str */
0877: if(optSTR->str==NULL) break;
0878: fprintf(stderr," str=\"%s\"\n",optSTR->str);
0879: break;
0880:
0881: case OSEL:
0882: optSEL=(MssOptSEL *)opt[i];
0883: fprintf(stderr,"(SEL) ");
0884: /* ####### set */
0885: if( optSEL->set ) fprintf(stderr,"--> set in command line\n");
0886: else fprintf(stderr,"--> not set in command line\n");
0887:
0888: /* ####### str */
0889: if(optSEL->str==NULL) break;
0890: fprintf(stderr," str=\"%s\"\n",optSEL->str);
0891: break;
0892:
0893: case OSLS:
0894: optSLS=(MssOptSLS *)opt[i];
0895: fprintf(stderr,"(SLS) ");
0896: /* ####### set */
0897: if( optSLS->set ) fprintf(stderr,"--> set in command line\n");
0898: else fprintf(stderr,"--> not set in command line\n");
0899:
0900: /* ####### str */
0901: if(optSLS->str==NULL) break;
0902: fprintf(stderr," str=\"%s\"\n",optSLS->str);
0903:
0904: /* ####### cnt */
0905: fprintf(stderr," cnt=%d\n",optSLS->cnt);
0906:
0907: /* ####### strList,colList */
0908: fprintf(stderr," strList,colList:\n");
0909: for(j=0; j<optSLS->cnt; j++){
0910: fprintf(stderr," [%d]=\"%s\",\"%s\"\n",j,
0911: *(optSLS->strList+j),
0912: *(optSLS->colList+j));
0913: }
0914: break;
0915:
0916: case OINT:
0917: optINT=(MssOptINT *)opt[i];
0918: fprintf(stderr,"(INT) ");
0919: /* ####### set */
0920: if( optINT->set ) fprintf(stderr,"--> set in command line\n");
0921: else fprintf(stderr,"--> not set in command line\n");
0922:
0923: /* ####### val */
0924: fprintf(stderr," val=%d\n",optINT->val );
0925: break;
0926:
0927: case OILS:
0928: optILS=(MssOptILS *)opt[i];
0929: fprintf(stderr,"(ILS) ");
0930: /* ####### set */
0931: if( optILS->set ) fprintf(stderr,"--> set in command line\n");
0932: else fprintf(stderr,"--> not set in command line\n");
0933:
0934: /* ####### str */
0935: if(optILS->str==NULL) break;
0936: fprintf(stderr," str=\"%s\"\n",optILS->str);
0937:
0938: /* ####### cnt */
0939: fprintf(stderr," cnt=%d\n",optILS->cnt);
0940:
0941: /* ####### val */
0942: fprintf(stderr," val:\n");
0943: for(j=0; j<optILS->cnt; j++){
0944: fprintf(stderr," [%d]=%d\n",j,*(optILS->val+j));
0945: }
0946: break;
0947:
0948: case ORNG:
0949: optRNG=(MssOptRNG *)opt[i];
0950: fprintf(stderr,"(RNG) ");
0951: /* ####### set */
0952: if( optRNG->set ) fprintf(stderr,"--> set in command line\n");
0953: else fprintf(stderr,"--> not set in command line\n");
0954:
0955: /* ####### str */
0956: if(optRNG->str==NULL) break;
0957: fprintf(stderr," str=\"%s\"\n",optRNG->str);
0958:
0959: /* ####### cnt */
0960: fprintf(stderr," cnt=%d\n",optRNG->cnt);
0961:
0962: /* ####### from,to */
0963: fprintf(stderr," from,to:\n");
0964: for(j=0; j<optRNG->cnt; j++){
0965: fprintf(stderr," [%d]=%d,%d\n",j,
0966: *(optRNG->from+j),
0967: *(optRNG->to +j));
0968: }
0969: break;
0970:
0971: case ODBL:
0972: optDBL=(MssOptDBL *)opt[i];
0973: fprintf(stderr,"(DBL) ");
0974: /* ####### set */
0975: if( optDBL->set ) fprintf(stderr,"--> set in command line\n");
0976: else fprintf(stderr,"--> not set in command line\n");
0977:
0978: /* ####### val */
0979: fprintf(stderr," val=%g\n",optDBL->val );
0980: break;
0981:
0982: case ODLS:
0983: optDLS=(MssOptDLS *)opt[i];
0984: fprintf(stderr,"(DLS) ");
0985: /* ####### set */
0986: if( optDLS->set ) fprintf(stderr,"--> set in command line\n");
0987: else fprintf(stderr,"--> not set in command line\n");
0988:
0989: /* ####### str */
0990: if(optDLS->str==NULL) break;
0991: fprintf(stderr," str=\"%s\"\n",optDLS->str);
0992:
0993: /* ####### cnt */
0994: fprintf(stderr," cnt=%d\n",optDLS->cnt);
0995:
0996: /* ####### val */
0997: fprintf(stderr," val:\n");
0998: for(j=0; j<optDLS->cnt; j++){
0999: fprintf(stderr," [%d]=%g\n",j,*(optDLS->val+j));
1000: }
1001: break;
1002:
1003: case OFLD:
1004: optFLD=(MssOptFLD *)opt[i];
1005: fprintf(stderr,"(FLD) ");
1006: /* ####### set */
1007: if( optFLD->set ) fprintf(stderr,"--> set in command line\n");
1008: else fprintf(stderr,"--> not set in command line\n");
1009:
1010: /* ####### str */
1011: if(optFLD->str==NULL) break;
1012: fprintf(stderr," str=\"%s\"\n",optFLD->str);
1013:
1014: /* ####### cnt */
1015: fprintf(stderr," cnt=%d\n",optFLD->cnt);
1016:
1017: /* ####### nam,fldOpt,newNam */
1018: fprintf(stderr," nam,fldOpt,newNam:\n");
1019: for(j=0; j<optFLD->cnt; j++){
1020: fprintf(stderr," [%d]=%s,%s,%s\n",j, *(optFLD->nam +j),
1021: *(optFLD->fldOpt+j),
1022: *(optFLD->newNam+j));
1023: }
1024:
1025: break;
1026:
1027: case OKEY:
1028: optKEY=(MssOptKEY *)opt[i];
1029: fprintf(stderr,"(KEY) ");
1030: /* ####### set */
1031: if( optKEY->set ) fprintf(stderr,"--> set in command line\n");
1032: else fprintf(stderr,"--> not set in command line\n");
1033:
1034: /* ####### str */
1035: if(optKEY->str==NULL) break;
1036: fprintf(stderr," str=\"%s\"\n",optKEY->str);
1037:
1038: /* ####### cnt */
1039: fprintf(stderr," cnt=%d\n",optKEY->cnt);
1040:
1041: /* ####### nam,fldOpt,newNam */
1042: for(j=0; j<optKEY->cnt; j++){
1043: fprintf(stderr," nam[%d]=%s\n",j, *(optKEY->nam +j));
1044: }
1045:
1046: break;
1047:
1048: case OINF:
1049: optINF=(MssOptINF *)opt[i];
1050: fprintf(stderr,"(INF) ");
1051: /* ####### set */
1052: if( optINF->set ) fprintf(stderr,"--> set in command line\n");
1053: else fprintf(stderr,"--> not set in command line\n");
1054:
1055: /* ####### str */
1056: if(optINF->str==NULL) break;
1057: fprintf(stderr," str=\"%s\"\n",optINF->str);
1058:
1059: /* ####### cnt */
1060: fprintf(stderr," cnt=%d\n",optINF->cnt);
1061:
1062: /* ####### strList */
1063: fprintf(stderr," strList:\n");
1064: for(j=0; j<optINF->cnt; j++){
1065: fprintf(stderr," [%d]=%s\n",j, *(optINF->strList+j));
1066: }
1067:
1068: break;
1069:
1070: case OOTF:
1071: optOTF=(MssOptOTF *)opt[i];
1072: fprintf(stderr,"(OTF) ");
1073: /* ####### set */
1074: if( optOTF->set ) fprintf(stderr,"--> set in command line\n");
1075: else fprintf(stderr,"--> not set in command line\n");
1076:
1077: /* ####### str */
1078: if(optOTF->str==NULL) break;
1079: fprintf(stderr," str=\"%s\"\n",optOTF->str);
1080: break;
1081:
1082: case OFLG:
1083: optFLG=(MssOptFLG *)opt[i];
1084: fprintf(stderr,"(FLG) ");
1085: /* ####### set */
1086: if( optFLG->set )
1087: fprintf(stderr,"--> set in command line\n");
1088: else
1089: fprintf(stderr,"--> not set in command line\n");
1090: break;
1091: }
1092:
1093: i++;
1094: }
1095: }
1096:
1097: /**
1098: * # FUNCTION #
1099: * mssComHelp構造体の内容からコマンドヘルプを表示する。
1100: */
1101: static void prnComHlp(void *opt[], struct mssComHelp *comHelp)
1102: {
1103: int optCnt=-1;
1104: int i,j;
1105: char *tmp;
1106: char *tmp2;
1107: char **list1;
1108: int list1Cnt;
1109: struct mssFPW *fpw;
1110: MssOptSTR *optSTR;
1111: MssOptSEL *optSEL;
1112: MssOptSLS *optSLS;
1113: MssOptINT *optINT;
1114: MssOptILS *optILS;
1115: MssOptRNG *optRNG;
1116: MssOptDBL *optDBL;
1117: MssOptDLS *optDLS;
1118: MssOptFLD *optFLD;
1119: MssOptKEY *optKEY;
1120: MssOptINF *optINF;
1121: MssOptOTF *optOTF;
1122: MssOptFLG *optFLG;
1123:
1124: fpw=mssOpenFPW((char *)1,0,0);
1125:
1126: /* オプションの数をカウントする */
1127: while( opt[++optCnt]!=NULL );
1128:
1129: /* ####### name */
1130: mssWriteStr("NAME:\n",fpw);
1131: mssWriteStr(comHelp->name,fpw);
1132: mssWriteStr(" ", fpw);
1133:
1134: /* ####### version */
1135: mssWriteStr("version: ",fpw);
1136: mssWriteStr(comHelp->version,fpw);
1137: mssWriteStr(" ", fpw);
1138:
1139: /* ####### title */
1140: if(mssIsValidStr(comHelp->title)){
1141: mssWriteStr(comHelp->title,fpw);
1142: }
1143: mssWriteRet(fpw);
1144: mssWriteRet(fpw);
1145:
1146: /* ####### USAGE: */
1147: mssWriteStr("USAGE:\n",fpw);
1148: mssWriteStr(comHelp->name,fpw);
1149: mssWriteStr(" ", fpw);
1150:
1151: /* ####### OPTION */
1152: for(i=0; i<optCnt; i++){
1153: switch( ((MssOptKEY *)opt[i])->type ){
1154: case OSTR:
1155: optSTR=(MssOptSTR *)opt[i];
1156: if(!optSTR->must ) mssWriteStr("[",fpw);
1157: mssWriteStr("-",fpw);
1158: mssWriteStr(optSTR->keyWord,fpw);
1159: mssWriteStr(" ", fpw);
1160: mssWriteStr(optSTR->title,fpw);
1161: if(!optSTR->must ) mssWriteStr("]",fpw);
1162: mssWriteStr(" ", fpw);
1163: break;
1164:
1165: case OSEL:
1166: optSEL=(MssOptSEL *)opt[i];
1167: if(!optSEL->must ) mssWriteStr("[",fpw);
1168: mssWriteStr("-",fpw);
1169: mssWriteStr(optSEL->keyWord,fpw);
1170: mssWriteStr(" ", fpw);
1171: mssWriteStr(optSEL->title,fpw);
1172: mssWriteStr("{",fpw);
1173: tmp=mssStrdup(optSEL->selList);
1174: tmp2=tmp;
1175: while(*tmp2!='\0'){
1176: if(*tmp2==',')*tmp2='|';
1177: tmp2++;
1178: }
1179: mssWriteStr(tmp,fpw);
1180: mssFree(tmp);
1181: mssWriteStr("}",fpw);
1182: if(!optSEL->must ) mssWriteStr("]",fpw);
1183: mssWriteStr(" ", fpw);
1184: break;
1185:
1186: case OSLS:
1187: optSLS=(MssOptSLS *)opt[i];
1188: if(!optSLS->must ) mssWriteStr("[",fpw);
1189: mssWriteStr("-",fpw);
1190: mssWriteStr(optSLS->keyWord,fpw);
1191: mssWriteStr(" ", fpw);
1192: mssWriteStr(optSLS->title,fpw);
1193: if(!optSLS->must ) mssWriteStr("]",fpw);
1194: mssWriteStr(" ", fpw);
1195: break;
1196:
1197: case OINT:
1198: optINT=(MssOptINT *)opt[i];
1199: if(!optINT->must ) mssWriteStr("[",fpw);
1200: mssWriteStr("-",fpw);
1201: mssWriteStr(optINT->keyWord,fpw);
1202: mssWriteStr(" ", fpw);
1203: mssWriteStr(optINT->title,fpw);
1204: if(!optINT->must ) mssWriteStr("]",fpw);
1205: mssWriteStr(" ", fpw);
1206: break;
1207:
1208: case OILS:
1209: optILS=(MssOptILS *)opt[i];
1210: if(!optILS->must ) mssWriteStr("[",fpw);
1211: mssWriteStr("-",fpw);
1212: mssWriteStr(optILS->keyWord,fpw);
1213: mssWriteStr(" ", fpw);
1214: mssWriteStr(optILS->title,fpw);
1215: if(!optILS->must ) mssWriteStr("]",fpw);
1216: mssWriteStr(" ", fpw);
1217: break;
1218:
1219: case ORNG:
1220: optRNG=(MssOptRNG *)opt[i];
1221: if(!optRNG->must ) mssWriteStr("[",fpw);
1222: mssWriteStr("-",fpw);
1223: mssWriteStr(optRNG->keyWord,fpw);
1224: mssWriteStr(" ", fpw);
1225: mssWriteStr(optRNG->title,fpw);
1226: if(!optRNG->must ) mssWriteStr("]",fpw);
1227: mssWriteStr(" ", fpw);
1228: break;
1229:
1230: case ODBL:
1231: optDBL=(MssOptDBL *)opt[i];
1232: if(!optDBL->must ) mssWriteStr("[",fpw);
1233: mssWriteStr("-",fpw);
1234: mssWriteStr(optDBL->keyWord,fpw);
1235: mssWriteStr(" ", fpw);
1236: mssWriteStr(optDBL->title,fpw);
1237: if(!optDBL->must ) mssWriteStr("]",fpw);
1238: mssWriteStr(" ", fpw);
1239: break;
1240:
1241: case ODLS:
1242: optDLS=(MssOptDLS *)opt[i];
1243: if(!optDLS->must ) mssWriteStr("[",fpw);
1244: mssWriteStr("-",fpw);
1245: mssWriteStr(optDLS->keyWord,fpw);
1246: mssWriteStr(" ", fpw);
1247: mssWriteStr(optDLS->title,fpw);
1248: if(!optDLS->must ) mssWriteStr("]",fpw);
1249: mssWriteStr(" ", fpw);
1250: break;
1251:
1252: case OFLD:
1253: optFLD=(MssOptFLD *)opt[i];
1254: if(!optFLD->must ) mssWriteStr("[",fpw);
1255: mssWriteStr("-",fpw);
1256: mssWriteStr(optFLD->keyWord,fpw);
1257: mssWriteStr(" ", fpw);
1258: mssWriteStr(optFLD->title,fpw);
1259: if(mssIsValidStr(optFLD->fldOptSel)){
1260: list1Cnt=0;
1261: list1=mssTokByChr(optFLD->fldOptSel,',',&list1Cnt,1);
1262: mssWriteStr("[%{",fpw);
1263: for(j=0; j<list1Cnt-1; j++){
1264: mssWriteStr(*(list1+j),fpw);
1265: mssWriteStr("|",fpw);
1266: }
1267: mssWriteStr(*(list1+j),fpw);
1268: mssWriteStr("}]",fpw);
1269: mssFree(*list1);
1270: mssFree(list1);
1271: }
1272: if(!optFLD->must ) mssWriteStr("]",fpw);
1273: mssWriteStr(" ", fpw);
1274: break;
1275:
1276: case OKEY:
1277: optKEY=(MssOptKEY *)opt[i];
1278: if(!optKEY->must ) mssWriteStr("[",fpw);
1279: mssWriteStr("-",fpw);
1280: mssWriteStr(optKEY->keyWord,fpw);
1281: mssWriteStr(" ", fpw);
1282: mssWriteStr(optKEY->title,fpw);
1283: if(!optKEY->must ) mssWriteStr("]",fpw);
1284: mssWriteStr(" ", fpw);
1285: break;
1286:
1287: case OINF:
1288: optINF=(MssOptINF *)opt[i];
1289: if(!optINF->must ) mssWriteStr("[",fpw);
1290: mssWriteStr("-",fpw);
1291: mssWriteStr(optINF->keyWord,fpw);
1292: mssWriteStr(" ", fpw);
1293: mssWriteStr(optINF->title,fpw);
1294: if(!optINF->must ) mssWriteStr("]",fpw);
1295: mssWriteStr(" ", fpw);
1296: break;
1297:
1298: case OOTF:
1299: optOTF=(MssOptOTF *)opt[i];
1300: if(!optOTF->must ) mssWriteStr("[",fpw);
1301: mssWriteStr("-",fpw);
1302: mssWriteStr(optOTF->keyWord,fpw);
1303: mssWriteStr(" ", fpw);
1304: mssWriteStr(optOTF->title,fpw);
1305: if(!optOTF->must ) mssWriteStr("]",fpw);
1306: mssWriteStr(" ", fpw);
1307: break;
1308:
1309: case OFLG:
1310: optFLG=(MssOptFLG *)opt[i];
1311: mssWriteStr("[",fpw);
1312: mssWriteStr("-",fpw);
1313: mssWriteStr(optFLG->keyWord,fpw);
1314: mssWriteStr("]",fpw);
1315: mssWriteStr(" ", fpw);
1316: break;
1317: }
1318: }
1319: mssWriteRet(fpw);
1320: mssWriteRet(fpw);
1321:
1322: /* ####### summary */
1323: if(mssIsValidStr(comHelp->summary)){
1324: mssWriteStr("SUMMARY:\n",fpw);
1325: mssWriteStr(comHelp->summary,fpw);
1326: mssWriteRet(fpw);
1327: mssWriteRet(fpw);
1328: }
1329:
1330: mssWriteStr("OPTION:\n",fpw);
1331: /* ####### OPTION */
1332: for(i=0; i<optCnt; i++){
1333: if( ((MssOptKEY *)opt[i])->type == OFLG ){
1334: optFLG=(MssOptFLG *)opt[i];
1335: mssWriteStr("-",fpw);
1336: mssWriteStr(optFLG->keyWord,fpw);
1337: mssWriteStr(": ",fpw);
1338: mssWriteStr(optFLG->title,fpw);
1339: mssWriteRet(fpw);
1340: }
1341: }
1342: mssWriteRet(fpw);
1343:
1344: /* ####### example */
1345: if(mssIsValidStr(comHelp->example)){
1346: mssWriteStr("EXAMPLES:\n",fpw);
1347: mssWriteStr(comHelp->example,fpw);
1348: mssWriteRet(fpw);
1349: }
1350:
1351: /* ####### homepage */
1352: if(mssIsValidStr(comHelp->homepage)){
1353: mssWriteStr("INFORMATION: <",fpw);
1354: mssWriteStr(comHelp->homepage,fpw);
1355: mssWriteStr(">\n",fpw);
1356: }
1357:
1358: /* ####### bugReport */
1359: if(mssIsValidStr(comHelp->bugReport)){
1360: mssWriteStr("BUG REPORT: <",fpw);
1361: mssWriteStr(comHelp->bugReport,fpw);
1362: mssWriteStr(">\n",fpw);
1363: }
1364:
1365: mssWriteRet(fpw);
1366: }
1367:
1368: /**
1369: * # FUNCTION #
1370: * mssComHelp構造体の内容からmanドキュメント(groff)を出力する。
1371: */
1372: static void prnMan(void *opt[], struct mssComHelp *comHelp)
1373: {
1374: int optCnt=-1;
1375: int i,j;
1376: char *tmp;
1377: char *tmp2;
1378: char **list1;
1379: int list1Cnt;
1380: struct mssFPW *fpw;
1381: MssOptSTR *optSTR;
1382: MssOptSEL *optSEL;
1383: MssOptSLS *optSLS;
1384: MssOptINT *optINT;
1385: MssOptILS *optILS;
1386: MssOptRNG *optRNG;
1387: MssOptDBL *optDBL;
1388: MssOptDLS *optDLS;
1389: MssOptFLD *optFLD;
1390: MssOptKEY *optKEY;
1391: MssOptINF *optINF;
1392: MssOptOTF *optOTF;
1393: MssOptFLG *optFLG;
1394:
1395: time_t long_time;
1396: struct tm *nt;
1397: char msg[100];
1398:
1399:
1400: fpw=mssOpenFPW((char *)1,0,0);
1401:
1402: /* オプションの数をカウントする */
1403: while( opt[++optCnt]!=NULL );
1404:
1405: /* ####### comment */
1406: mssWriteStr(".\\Generated by xtcmd(",fpw);
1407: mssWriteStr("). Modify the source.\n\n",fpw);
1408:
1409: /* ####### .TH*/
1410: time(&long_time);
1411: nt = localtime(&long_time);
1412: mssWriteStr(".TH ",fpw);
1413: mssWriteStr(comHelp->name,fpw);
1414: mssWriteStr(" 1 \"",fpw);
1415: sprintf(msg, "%04d-%02d-%02d", nt->tm_year+1900,nt->tm_mon+1,nt->tm_mday);
1416: mssWriteStr(msg,fpw);
1417: mssWriteStr("\" ",fpw);
1418: mssWriteStr("MUSASHI",fpw);
1419: mssWriteRet(fpw); mssWriteRet(fpw);
1420:
1421: /* ####### .SH 名前 */
1422: /*mssWriteStr(".SH 名前\n",fpw);*/
1423: mssWriteStr(".SH NAME\n",fpw);
1424: mssWriteStr(comHelp->name,fpw);
1425: mssWriteStr(" \\- ",fpw);
1426: if(mssIsValidStr(comHelp->title)){
1427: mssWriteStr(comHelp->title,fpw);
1428: mssWriteRet(fpw);
1429: }else{
1430: mssWriteStr("noData\n",fpw);
1431: }
1432: mssWriteRet(fpw);
1433:
1434: /* ####### .SH 書式: */
1435: /*mssWriteStr(".SH 書式\n",fpw);*/
1436: mssWriteStr(".SH SYNOPSIS\n",fpw);
1437: mssWriteStr(comHelp->name,fpw);
1438: mssWriteStr(" ", fpw);
1439:
1440: for(i=0; i<optCnt; i++){
1441: switch( ((MssOptKEY *)opt[i])->type ){
1442: case OSTR:
1443: optSTR=(MssOptSTR *)opt[i];
1444: if(!optSTR->must ) mssWriteStr("[",fpw);
1445: mssWriteStr("-",fpw);
1446: mssWriteStr(optSTR->keyWord,fpw);
1447: mssWriteStr(" ", fpw);
1448: mssWriteStr(optSTR->title,fpw);
1449: if(!optSTR->must ) mssWriteStr("]",fpw);
1450: mssWriteStr(" ", fpw);
1451: break;
1452:
1453: case OSEL:
1454: optSEL=(MssOptSEL *)opt[i];
1455: if(!optSEL->must ) mssWriteStr("[",fpw);
1456: mssWriteStr("-",fpw);
1457: mssWriteStr(optSEL->keyWord,fpw);
1458: mssWriteStr(" ", fpw);
1459: mssWriteStr(optSEL->title,fpw);
1460: mssWriteStr("{",fpw);
1461: tmp=mssStrdup(optSEL->selList);
1462: tmp2=tmp;
1463: while(*tmp2!='\0'){
1464: if(*tmp2==',')*tmp2='|';
1465: tmp2++;
1466: }
1467: mssWriteStr(tmp,fpw);
1468: mssFree(tmp);
1469: mssWriteStr("}",fpw);
1470: if(!optSEL->must ) mssWriteStr("]",fpw);
1471: mssWriteStr(" ", fpw);
1472: break;
1473:
1474: case OSLS:
1475: optSLS=(MssOptSLS *)opt[i];
1476: if(!optSLS->must ) mssWriteStr("[",fpw);
1477: mssWriteStr("-",fpw);
1478: mssWriteStr(optSLS->keyWord,fpw);
1479: mssWriteStr(" ", fpw);
1480: mssWriteStr(optSLS->title,fpw);
1481: if(!optSLS->must ) mssWriteStr("]",fpw);
1482: mssWriteStr(" ", fpw);
1483: break;
1484:
1485: case OINT:
1486: optINT=(MssOptINT *)opt[i];
1487: if(!optINT->must ) mssWriteStr("[",fpw);
1488: mssWriteStr("-",fpw);
1489: mssWriteStr(optINT->keyWord,fpw);
1490: mssWriteStr(" ", fpw);
1491: mssWriteStr(optINT->title,fpw);
1492: if(!optINT->must ) mssWriteStr("]",fpw);
1493: mssWriteStr(" ", fpw);
1494: break;
1495:
1496: case OILS:
1497: optILS=(MssOptILS *)opt[i];
1498: if(!optILS->must ) mssWriteStr("[",fpw);
1499: mssWriteStr("-",fpw);
1500: mssWriteStr(optILS->keyWord,fpw);
1501: mssWriteStr(" ", fpw);
1502: mssWriteStr(optILS->title,fpw);
1503: if(!optILS->must ) mssWriteStr("]",fpw);
1504: mssWriteStr(" ", fpw);
1505: break;
1506:
1507: case ORNG:
1508: optRNG=(MssOptRNG *)opt[i];
1509: if(!optRNG->must ) mssWriteStr("[",fpw);
1510: mssWriteStr("-",fpw);
1511: mssWriteStr(optRNG->keyWord,fpw);
1512: mssWriteStr(" ", fpw);
1513: mssWriteStr(optRNG->title,fpw);
1514: if(!optRNG->must ) mssWriteStr("]",fpw);
1515: mssWriteStr(" ", fpw);
1516: break;
1517:
1518: case ODBL:
1519: optDBL=(MssOptDBL *)opt[i];
1520: if(!optDBL->must ) mssWriteStr("[",fpw);
1521: mssWriteStr("-",fpw);
1522: mssWriteStr(optDBL->keyWord,fpw);
1523: mssWriteStr(" ", fpw);
1524: mssWriteStr(optDBL->title,fpw);
1525: if(!optDBL->must ) mssWriteStr("]",fpw);
1526: mssWriteStr(" ", fpw);
1527: break;
1528:
1529: case ODLS:
1530: optDLS=(MssOptDLS *)opt[i];
1531: if(!optDLS->must ) mssWriteStr("[",fpw);
1532: mssWriteStr("-",fpw);
1533: mssWriteStr(optDLS->keyWord,fpw);
1534: mssWriteStr(" ", fpw);
1535: mssWriteStr(optDLS->title,fpw);
1536: if(!optDLS->must ) mssWriteStr("]",fpw);
1537: mssWriteStr(" ", fpw);
1538: break;
1539:
1540: case OFLD:
1541: optFLD=(MssOptFLD *)opt[i];
1542: if(!optFLD->must ) mssWriteStr("[",fpw);
1543: mssWriteStr("-",fpw);
1544: mssWriteStr(optFLD->keyWord,fpw);
1545: mssWriteStr(" ", fpw);
1546: mssWriteStr(optFLD->title,fpw);
1547: if(mssIsValidStr(optFLD->fldOptSel)){
1548: list1Cnt=0;
1549: list1=mssTokByChr(optFLD->fldOptSel,',',&list1Cnt,1);
1550: mssWriteStr("[%{",fpw);
1551: for(j=0; j<list1Cnt-1; j++){
1552: mssWriteStr(*(list1+j),fpw);
1553: mssWriteStr("|",fpw);
1554: }
1555: mssWriteStr(*(list1+j),fpw);
1556: mssWriteStr("}]",fpw);
1557: mssFree(*list1);
1558: mssFree(list1);
1559: }
1560: if(!optFLD->must ) mssWriteStr("]",fpw);
1561: mssWriteStr(" ", fpw);
1562: break;
1563:
1564: case OKEY:
1565: optKEY=(MssOptKEY *)opt[i];
1566: if(!optKEY->must ) mssWriteStr("[",fpw);
1567: mssWriteStr("-",fpw);
1568: mssWriteStr(optKEY->keyWord,fpw);
1569: mssWriteStr(" ", fpw);
1570: mssWriteStr(optKEY->title,fpw);
1571: if(!optKEY->must ) mssWriteStr("]",fpw);
1572: mssWriteStr(" ", fpw);
1573: break;
1574:
1575: case OINF:
1576: optINF=(MssOptINF *)opt[i];
1577: if(!optINF->must ) mssWriteStr("[",fpw);
1578: mssWriteStr("-",fpw);
1579: mssWriteStr(optINF->keyWord,fpw);
1580: mssWriteStr(" ", fpw);
1581: mssWriteStr(optINF->title,fpw);
1582: if(!optINF->must ) mssWriteStr("]",fpw);
1583: mssWriteStr(" ", fpw);
1584: break;
1585:
1586: case OOTF:
1587: optOTF=(MssOptOTF *)opt[i];
1588: if(!optOTF->must ) mssWriteStr("[",fpw);
1589: mssWriteStr("-",fpw);
1590: mssWriteStr(optOTF->keyWord,fpw);
1591: mssWriteStr(" ", fpw);
1592: mssWriteStr(optOTF->title,fpw);
1593: if(!optOTF->must ) mssWriteStr("]",fpw);
1594: mssWriteStr(" ", fpw);
1595: break;
1596:
1597: case OFLG:
1598: optFLG=(MssOptFLG *)opt[i];
1599: mssWriteStr("[",fpw);
1600: mssWriteStr("-",fpw);
1601: mssWriteStr(optFLG->keyWord,fpw);
1602: mssWriteStr("]",fpw);
1603: mssWriteStr(" ", fpw);
1604: break;
1605: }
1606: }
1607: mssWriteRet(fpw);
1608: mssWriteRet(fpw);
1609:
1610: /* ####### .SH 説明 */
1611: if(mssIsValidStr(comHelp->summary)){
1612: /*mssWriteStr(".SH 説明\n",fpw);*/
1613: mssWriteStr(".SH DESCRIPTION\n",fpw);
1614: mssWriteStr(comHelp->summary,fpw);
1615: mssWriteRet(fpw);
1616: mssWriteRet(fpw);
1617: }
1618:
1619:
1620: /* ####### .SH パラメータ */
1621: /*mssWriteStr(".SH パラメータ\n",fpw);*/
1622: mssWriteStr(".SH PARAMETERS\n",fpw);
1623: for(i=0; i<optCnt; i++){
1624: if( ((MssOptKEY *)opt[i])->type != OFLG ){
1625: switch( ((MssOptKEY *)opt[i])->type ){
1626: case OSTR:
1627: optSTR=(MssOptSTR *)opt[i];
1628: mssWriteStr(".IP \"-",fpw);
1629: mssWriteStr(optSTR->keyWord,fpw); mssWriteStr(" ",fpw);
1630: mssWriteStr(optSTR->title,fpw) ; mssWriteStr("\"\n",fpw);
1631: mssWriteStr(optSTR->comment,fpw); mssWriteRet(fpw);
1632: break;
1633: case OSEL:
1634: optSEL=(MssOptSEL *)opt[i];
1635: mssWriteStr(".IP \"-",fpw);
1636: mssWriteStr(optSEL->keyWord,fpw); mssWriteStr(" ",fpw);
1637: mssWriteStr(optSEL->title,fpw) ; mssWriteStr("\"\n",fpw);
1638: mssWriteStr(optSEL->comment,fpw); mssWriteRet(fpw);
1639: break;
1640: case OSLS:
1641: optSLS=(MssOptSLS *)opt[i];
1642: mssWriteStr(".IP \"-",fpw);
1643: mssWriteStr(optSLS->keyWord,fpw); mssWriteStr(" ",fpw);
1644: mssWriteStr(optSLS->title,fpw) ; mssWriteStr("\"\n",fpw);
1645: mssWriteStr(optSLS->comment,fpw); mssWriteRet(fpw);
1646: break;
1647: case OINT:
1648: optINT=(MssOptINT *)opt[i];
1649: mssWriteStr(".IP \"-",fpw);
1650: mssWriteStr(optINT->keyWord,fpw); mssWriteStr(" ",fpw);
1651: mssWriteStr(optINT->title,fpw) ; mssWriteStr("\"\n",fpw);
1652: mssWriteStr(optINT->comment,fpw); mssWriteRet(fpw);
1653: break;
1654: case OILS:
1655: optILS=(MssOptILS *)opt[i];
1656: mssWriteStr(".IP \"-",fpw);
1657: mssWriteStr(optILS->keyWord,fpw); mssWriteStr(" ",fpw);
1658: mssWriteStr(optILS->title,fpw) ; mssWriteStr("\"\n",fpw);
1659: mssWriteStr(optILS->comment,fpw); mssWriteRet(fpw);
1660: break;
1661: case ORNG:
1662: optRNG=(MssOptRNG *)opt[i];
1663: mssWriteStr(".IP \"-",fpw);
1664: mssWriteStr(optRNG->keyWord,fpw); mssWriteStr(" ",fpw);
1665: mssWriteStr(optRNG->title,fpw) ; mssWriteStr("\"\n",fpw);
1666: mssWriteStr(optRNG->comment,fpw); mssWriteRet(fpw);
1667: break;
1668: case ODBL:
1669: optDBL=(MssOptDBL *)opt[i];
1670: mssWriteStr(".IP \"-",fpw);
1671: mssWriteStr(optDBL->keyWord,fpw); mssWriteStr(" ",fpw);
1672: mssWriteStr(optDBL->title,fpw) ; mssWriteStr("\"\n",fpw);
1673: mssWriteStr(optDBL->comment,fpw); mssWriteRet(fpw);
1674: break;
1675: case ODLS:
1676: optDLS=(MssOptDLS *)opt[i];
1677: mssWriteStr(".IP \"-",fpw);
1678: mssWriteStr(optDLS->keyWord,fpw); mssWriteStr(" ",fpw);
1679: mssWriteStr(optDLS->title,fpw) ; mssWriteStr("\"\n",fpw);
1680: mssWriteStr(optDLS->comment,fpw); mssWriteRet(fpw);
1681: break;
1682: case OFLD:
1683: optFLD=(MssOptFLD *)opt[i];
1684: mssWriteStr(".IP \"-",fpw);
1685: mssWriteStr(optFLD->keyWord,fpw); mssWriteStr(" ",fpw);
1686: mssWriteStr(optFLD->title,fpw) ; mssWriteStr("\"\n",fpw);
1687: mssWriteStr(optFLD->comment,fpw); mssWriteRet(fpw);
1688: break;
1689: case OKEY:
1690: optKEY=(MssOptKEY *)opt[i];
1691: mssWriteStr(".IP \"-",fpw);
1692: mssWriteStr(optKEY->keyWord,fpw); mssWriteStr(" ",fpw);
1693: mssWriteStr(optKEY->title,fpw) ; mssWriteStr("\"\n",fpw);
1694: mssWriteStr(optKEY->comment,fpw); mssWriteRet(fpw);
1695: break;
1696: case OINF:
1697: optINF=(MssOptINF *)opt[i];
1698: mssWriteStr(".IP \"-",fpw);
1699: mssWriteStr(optINF->keyWord,fpw); mssWriteStr(" ",fpw);
1700: mssWriteStr(optINF->title,fpw) ; mssWriteStr("\"\n",fpw);
1701: mssWriteStr(optINF->comment,fpw); mssWriteRet(fpw);
1702: break;
1703: case OOTF:
1704: optOTF=(MssOptOTF *)opt[i];
1705: mssWriteStr(".IP \"-",fpw);
1706: mssWriteStr(optOTF->keyWord,fpw); mssWriteStr(" ",fpw);
1707: mssWriteStr(optOTF->title,fpw) ; mssWriteStr("\"\n",fpw);
1708: mssWriteStr(optOTF->comment,fpw); mssWriteRet(fpw);
1709: break;
1710: case OFLG:
1711: break;
1712: }
1713: }
1714: }
1715: mssWriteRet(fpw);
1716:
1717: /* ####### .SH オプション */
1718: /*mssWriteStr(".SH オプション\n",fpw);*/
1719: mssWriteStr(".SH OPTIONS\n",fpw);
1720: for(i=0; i<optCnt; i++){
1721: if( ((MssOptKEY *)opt[i])->type == OFLG ){
1722: optFLG=(MssOptFLG *)opt[i];
1723: mssWriteStr(".IP \"-",fpw);
1724: mssWriteStr(optFLG->keyWord,fpw);
1725: mssWriteStr("\"\n",fpw);
1726: mssWriteStr(optFLG->title,fpw);
1727: mssWriteStr(": ",fpw);
1728: mssWriteStr(optFLG->comment,fpw);
1729: mssWriteRet(fpw);
1730: }
1731: }
1732: mssWriteRet(fpw);
1733:
1734: /* ####### .SH 利用例 */
1735: if(mssIsValidStr(comHelp->example)){
1736: /*mssWriteStr(".SH 利用例\n",fpw);*/
1737: mssWriteStr(".SH EXAMPLE\n",fpw);
1738: list1Cnt=0;
1739: list1=mssTokByChr(comHelp->example,'\n',&list1Cnt,1);
1740: for(j=0; j<list1Cnt; j++){
1741: if(mssIsValidStr(*(list1+j)) ){
1742: mssWriteStr(".P\n",fpw);
1743: mssWriteStr(" ", fpw);
1744: mssWriteStr(*(list1+j),fpw);
1745: mssWriteRet(fpw);
1746: }
1747: }
1748: mssFree(*list1);
1749: mssFree(list1);
1750: mssWriteRet(fpw);
1751: }
1752:
1753: /* ####### .SH 参照 */
1754: if(mssIsValidStr(comHelp->example)){
1755: /*mssWriteStr(".SH 参照\n",fpw);*/
1756: mssWriteStr(".SH SEE ALSO\n",fpw);
1757: list1Cnt=0;
1758: list1=mssTokByChr(comHelp->reference,',',&list1Cnt,1);
1759: for(j=0; j<list1Cnt; j++){
1760: if(mssIsValidStr(*(list1+j)) ){
1761: mssWriteStr(".BR ",fpw);
1762: mssWriteStr(*(list1+j),fpw);
1763: if(j==list1Cnt-1){
1764: mssWriteStr(" (1)\n",fpw);
1765: }else{
1766: mssWriteStr(" (1),\n",fpw);
1767: }
1768: }
1769: }
1770: mssFree(*list1);
1771: mssFree(list1);
1772: mssWriteRet(fpw);
1773: }
1774:
1775:
1776: /* ####### .SH webページ */
1777: if(mssIsValidStr(comHelp->homepage)){
1778: /*mssWriteStr(".SH webページ\n",fpw);*/
1779: mssWriteStr(".SH WEB PAGE\n",fpw);
1780: mssWriteStr(comHelp->homepage,fpw);
1781: mssWriteRet(fpw); mssWriteRet(fpw);
1782: }
1783:
1784: /* ####### .SH バグ報告 */
1785: if(mssIsValidStr(comHelp->bugReport)){
1786: /*mssWriteStr(".SH バグ報告\n",fpw);*/
1787: mssWriteStr(".SH BUG REPORT\n",fpw);
1788: mssWriteStr(comHelp->bugReport,fpw);
1789: mssWriteRet(fpw); mssWriteRet(fpw);
1790: }
1791:
1792: /* ####### .SH 作者 */
1793: if(mssIsValidStr(comHelp->example)){
1794: /*mssWriteStr(".SH 作者\n",fpw);*/
1795: mssWriteStr(".SH AUTHORS\n",fpw);
1796: mssWriteStr(comHelp->author,fpw);
1797: mssWriteRet(fpw);
1798: }
1799: }
1800:
1801: /**
1802: * # FUNCTION #
1803: * mssComHelp構造体の内容からXMLドキュメントを出力する。
1804: */
1805: static void prnComXml(void *opt[], struct mssComHelp *comHelp)
1806: {
1807: int optCnt=-1;
1808: int i,j;
1809: struct mssFPW *fpw;
1810: char **list1;
1811: int list1Cnt;
1812: char **list2;
1813: int list2Cnt;
1814: MssOptSTR *optSTR;
1815: MssOptSEL *optSEL;
1816: MssOptSLS *optSLS;
1817: MssOptINT *optINT;
1818: MssOptILS *optILS;
1819: MssOptRNG *optRNG;
1820: MssOptDBL *optDBL;
1821: MssOptDLS *optDLS;
1822: MssOptFLD *optFLD;
1823: MssOptKEY *optKEY;
1824: MssOptINF *optINF;
1825: MssOptOTF *optOTF;
1826: MssOptFLG *optFLG;
1827:
1828: struct mssXmlTag *commandTag;
1829: struct mssXmlTag *referTag;
1830: struct mssXmlTag *authorTag;
1831: struct mssXmlTag *exampleTag;
1832: struct mssXmlTag *optionTag;
1833: struct mssXmlTag *xmlTag;
1834: struct mssXmlTag *manTag;
1835:
1836: fpw=mssOpenFPW((char *)1,0,0);
1837: manTag=mssInitXmlTag("mandatory",NULL);
1838:
1839: /* オプションの数をカウントする */
1840: while( opt[++optCnt]!=NULL );
1841:
1842: /* <?xml version="1.0" encoding="EUC-JP"?> */
1843: mssWriteXmlDeclaration( MssXmlDefVer, MssXmlDefEnc ,fpw);
1844:
1845: /* <command name="xtcut" version="3.00"> */
1846: commandTag=mssInitXmlTag("command",NULL);
1847: mssAddXmlTagAttributeStr(commandTag,"name" ,comHelp->name,NULL);
1848: mssAddXmlTagAttributeStr(commandTag,"version",comHelp->version,NULL);
1849: mssWriteXmlStartTag(commandTag,NULL,fpw);
1850: mssWriteRet(fpw);
1851:
1852: /* ####### title */
1853: if(mssIsValidStr(comHelp->title)){
1854: mssWriteXmlTagStr(1,"title",comHelp->title,1,NULL,fpw);
1855: }
1856:
1857: /* ####### summary */
1858: if(mssIsValidStr(comHelp->summary)){
1859: mssWriteXmlTagStr(1,"summary",comHelp->summary,1,NULL,fpw);
1860: }
1861:
1862: /* ####### reference */
1863: if(mssIsValidStr(comHelp->reference)){
1864: list1Cnt=0;
1865: list1=mssTokByChr(comHelp->reference,',',&list1Cnt,1);
1866: for(j=0; j<list1Cnt; j++){
1867: mssWriteXmlIndent(1,fpw);
1868: referTag=mssInitXmlTag("reference",NULL);
1869: mssAddXmlTagAttributeInt(referTag,"no", j+1,NULL);
1870: mssWriteXmlStartTag(referTag,NULL,fpw);
1871: mssWriteXmlContent(*(list1+j),NULL,fpw);
1872: mssWriteXmlEndTag(referTag,NULL,fpw);
1873: mssWriteRet(fpw);
1874: mssFreeXmlTag(referTag);
1875: }
1876: mssFree(*list1);
1877: mssFree(list1);
1878: }
1879:
1880: /* ####### author */
1881: if(mssIsValidStr(comHelp->author)){
1882: list1Cnt=0;
1883: list1=mssTokByChr(comHelp->author,',',&list1Cnt,1);
1884: for(j=0; j<list1Cnt; j++){
1885: mssWriteXmlIndent(1,fpw);
1886: authorTag=mssInitXmlTag("author",NULL);
1887: mssAddXmlTagAttributeInt(authorTag,"no", j+1,NULL);
1888: mssWriteXmlStartTag(authorTag,NULL,fpw);
1889: mssWriteXmlContent(*(list1+j),NULL,fpw);
1890: mssWriteXmlEndTag(authorTag,NULL,fpw);
1891: mssWriteRet(fpw);
1892: mssFreeXmlTag(authorTag);
1893: }
1894: mssFree(*list1);
1895: mssFree(list1);
1896: }
1897:
1898: /* ####### example */
1899: if(mssIsValidStr(comHelp->example)){
1900: list1Cnt=0;
1901: list1=mssTokByChr(comHelp->example,',',&list1Cnt,1);
1902: for(j=0; j<list1Cnt; j++){
1903: mssWriteXmlIndent(1,fpw);
1904: exampleTag=mssInitXmlTag("example",NULL);
1905: mssAddXmlTagAttributeInt(exampleTag,"no", j+1,NULL);
1906: mssWriteXmlStartTag(exampleTag,NULL,fpw);
1907: mssWriteXmlContent(*(list1+j),NULL,fpw);
1908: mssWriteXmlEndTag(exampleTag,NULL,fpw);
1909: mssWriteRet(fpw);
1910: mssFreeXmlTag(exampleTag);
1911: }
1912: mssFree(*list1);
1913: mssFree(list1);
1914: }
1915:
1916: /* ####### bugReport */
1917: if(mssIsValidStr(comHelp->bugReport)){
1918: mssWriteXmlTagStr(1,"bugReport",comHelp->bugReport,1,NULL,fpw);
1919: }
1920:
1921: /* ####### homepage */
1922: if(mssIsValidStr(comHelp->homepage)){
1923: mssWriteXmlTagStr(1,"homepage",comHelp->homepage,1,NULL,fpw);
1924: }
1925:
1926: /* ####### OPTION */
1927: for(i=0; i<optCnt; i++){
1928: mssWriteXmlIndent(1,fpw);
1929: optionTag=mssInitXmlTag("option",NULL);
1930: mssAddXmlTagAttributeStr(optionTag,"keyword", ((MssOptKEY *)opt[i])->keyWord,NULL);
1931: mssWriteXmlStartTag(optionTag,NULL,fpw);
1932: mssWriteRet(fpw);
1933:
1934: switch( ((MssOptKEY *)opt[i])->type ){
1935: case OSTR:
1936: optSTR=(MssOptSTR *)opt[i];
1937: mssWriteXmlTagStr(2,"type" ,"STR" ,1,NULL,fpw);
1938: mssWriteXmlTagFlg(2,"mandatory",optSTR->must ,1,NULL,fpw);
1939: mssWriteXmlTagStr(2,"default" ,optSTR->def ,1,NULL,fpw);
1940: mssWriteXmlTagInt(2,"minLen" ,optSTR->minLen ,1,NULL,fpw);
1941: mssWriteXmlTagInt(2,"maxLen" ,optSTR->maxLen ,1,NULL,fpw);
1942: mssWriteXmlTagStr(2,"title" ,optSTR->title ,1,NULL,fpw);
1943: mssWriteXmlTagStr(2,"comment" ,optSTR->comment,1,NULL,fpw);
1944: break;
1945:
1946: case OSEL:
1947: optSEL=(MssOptSEL *)opt[i];
1948: mssWriteXmlTagStr(2,"type" ,"SEL" ,1,NULL,fpw);
1949: mssWriteXmlTagFlg(2,"mandatory",optSEL->must ,1,NULL,fpw);
1950: mssWriteXmlTagStr(2,"default" ,optSEL->def ,1,NULL,fpw);
1951: mssWriteXmlTagStr(2,"title" ,optSEL->title ,1,NULL,fpw);
1952: mssWriteXmlTagStr(2,"comment" ,optSEL->comment,1,NULL,fpw);
1953:
1954: /* ####### selList,selListTitle */
1955: if(mssIsValidStr(optSEL->selList)){
1956: list1Cnt=0;
1957: list1=mssTokByChr(optSEL->selList,',',&list1Cnt,1);
1958: list2Cnt=0;
1959: list2=mssTokByChr(optSEL->selListTitle,',',&list2Cnt,1);
1960: for(j=0; j<list1Cnt; j++){
1961: mssWriteXmlIndent(2,fpw);
1962: xmlTag=mssInitXmlTag("selectList",NULL);
1963: mssAddXmlTagAttributeInt(xmlTag,"no" , j+1,NULL);
1964: mssAddXmlTagAttributeStr(xmlTag,"keyword", *(list1+j),NULL);
1965: mssWriteXmlStartTag(xmlTag,NULL,fpw);
1966: if(j<list2Cnt) mssWriteXmlContent(*(list2+j),NULL,fpw);
1967: mssWriteXmlEndTag(xmlTag,NULL,fpw);
1968: mssWriteRet(fpw);
1969: mssFreeXmlTag(xmlTag);
1970: }
1971: mssFree(*list1); mssFree(list1);
1972: mssFree(*list2); mssFree(list2);
1973: }
1974: break;
1975:
1976:
1977: case OSLS:
1978: optSLS=(MssOptSLS *)opt[i];
1979: mssWriteXmlTagStr(2,"type" ,"SLS" ,1,NULL,fpw);
1980: mssWriteXmlTagFlg(2,"mandatory",optSLS->must ,1,NULL,fpw);
1981: mssWriteXmlTagStr(2,"default" ,optSLS->def ,1,NULL,fpw);
1982: mssWriteXmlTagInt(2,"maxCnt" ,optSLS->maxCnt ,1,NULL,fpw);
1983: mssWriteXmlTagInt(2,"minLen" ,optSLS->minLen ,1,NULL,fpw);
1984: mssWriteXmlTagInt(2,"maxLen" ,optSLS->maxLen ,1,NULL,fpw);
1985: mssWriteXmlTagFlg(2,"colFlg" ,optSLS->colFlg ,1,NULL,fpw);
1986: mssWriteXmlTagStr(2,"title" ,optSLS->title ,1,NULL,fpw);
1987: mssWriteXmlTagStr(2,"comment" ,optSLS->comment,1,NULL,fpw);
1988: break;
1989:
1990: case OINT:
1991: optINT=(MssOptINT *)opt[i];
1992: mssWriteXmlTagStr(2,"type" ,"INT" ,1,NULL,fpw);
1993: mssWriteXmlTagFlg(2,"mandatory",optINT->must ,1,NULL,fpw);
1994: mssWriteXmlTagInt(2,"default" ,optINT->def ,1,NULL,fpw);
1995: mssWriteXmlTagInt(2,"min" ,optINT->min ,1,NULL,fpw);
1996: mssWriteXmlTagInt(2,"max" ,optINT->max ,1,NULL,fpw);
1997: mssWriteXmlTagStr(2,"title" ,optINT->title ,1,NULL,fpw);
1998: mssWriteXmlTagStr(2,"comment" ,optINT->comment,1,NULL,fpw);
1999: break;
2000:
2001: case OILS:
2002: optILS=(MssOptILS *)opt[i];
2003: mssWriteXmlTagStr(2,"type" ,"ILS" ,1,NULL,fpw);
2004: mssWriteXmlTagFlg(2,"mandatory",optILS->must ,1,NULL,fpw);
2005: mssWriteXmlTagStr(2,"default" ,optILS->def ,1,NULL,fpw);
2006: mssWriteXmlTagInt(2,"maxCnt" ,optILS->maxCnt ,1,NULL,fpw);
2007: mssWriteXmlTagInt(2,"min" ,optILS->min ,1,NULL,fpw);
2008: mssWriteXmlTagInt(2,"max" ,optILS->max ,1,NULL,fpw);
2009: mssWriteXmlTagStr(2,"title" ,optILS->title ,1,NULL,fpw);
2010: mssWriteXmlTagStr(2,"comment" ,optILS->comment,1,NULL,fpw);
2011: break;
2012:
2013: case ORNG:
2014: optRNG=(MssOptRNG *)opt[i];
2015: mssWriteXmlTagStr(2,"type" ,"RNG" ,1,NULL,fpw);
2016: mssWriteXmlTagFlg(2,"mandatory",optRNG->must ,1,NULL,fpw);
2017: mssWriteXmlTagStr(2,"default" ,optRNG->def ,1,NULL,fpw);
2018: mssWriteXmlTagInt(2,"maxCnt" ,optRNG->maxCnt ,1,NULL,fpw);
2019: mssWriteXmlTagInt(2,"min" ,optRNG->min ,1,NULL,fpw);
2020: mssWriteXmlTagInt(2,"max" ,optRNG->max ,1,NULL,fpw);
2021: mssWriteXmlTagStr(2,"title" ,optRNG->title ,1,NULL,fpw);
2022: mssWriteXmlTagStr(2,"comment" ,optRNG->comment,1,NULL,fpw);
2023: break;
2024:
2025: case ODBL:
2026: optDBL=(MssOptDBL *)opt[i];
2027: mssWriteXmlTagStr(2,"type" ,"DBL" ,1,NULL,fpw);
2028: mssWriteXmlTagFlg(2,"mandatory",optDBL->must ,1,NULL,fpw);
2029: mssWriteXmlTagDbl(2,"default" ,optDBL->def ,1,NULL,fpw);
2030: mssWriteXmlTagDbl(2,"min" ,optDBL->min ,1,NULL,fpw);
2031: mssWriteXmlTagDbl(2,"max" ,optDBL->max ,1,NULL,fpw);
2032: mssWriteXmlTagStr(2,"title" ,optDBL->title ,1,NULL,fpw);
2033: mssWriteXmlTagStr(2,"comment" ,optDBL->comment,1,NULL,fpw);
2034: break;
2035:
2036: case ODLS:
2037: optDLS=(MssOptDLS *)opt[i];
2038: mssWriteXmlTagStr(2,"type" ,"DLS" ,1,NULL,fpw);
2039: mssWriteXmlTagFlg(2,"mandatory",optDLS->must ,1,NULL,fpw);
2040: mssWriteXmlTagStr(2,"default" ,optDLS->def ,1,NULL,fpw);
2041: mssWriteXmlTagInt(2,"maxCnt" ,optDLS->maxCnt ,1,NULL,fpw);
2042: mssWriteXmlTagDbl(2,"min" ,optDLS->min ,1,NULL,fpw);
2043: mssWriteXmlTagDbl(2,"max" ,optDLS->max ,1,NULL,fpw);
2044: mssWriteXmlTagStr(2,"title" ,optDLS->title ,1,NULL,fpw);
2045: mssWriteXmlTagStr(2,"comment" ,optDLS->comment,1,NULL,fpw);
2046: break;
2047:
2048: case OFLD:
2049: optFLD=(MssOptFLD *)opt[i];
2050: mssWriteXmlTagStr(2,"type" ,"FLD" ,1,NULL,fpw);
2051: mssWriteXmlTagFlg(2,"mandatory" ,optFLD->must ,1,NULL,fpw);
2052: mssWriteXmlTagInt(2,"maxCnt" ,optFLD->maxCnt ,1,NULL,fpw);
2053: mssWriteXmlTagStr(2,"inKeyword" ,optFLD->inKeyWord,1,NULL,fpw);
2054: mssWriteXmlTagFlg(2,"newFieldNameFlg",optFLD->newFlg ,1,NULL,fpw);
2055: mssWriteXmlTagStr(2,"title" ,optFLD->title ,1,NULL,fpw);
2056: mssWriteXmlTagStr(2,"comment" ,optFLD->comment ,1,NULL,fpw);
2057:
2058: /* ####### fldOptTitle */
2059: if(mssIsValidStr(optFLD->fldOptSel)){
2060: list1Cnt=0;
2061: list1=mssTokByChr(optFLD->fldOptTitle,',',&list1Cnt,1);
2062: list2Cnt=0;
2063: list2=mssTokByChr(optFLD->fldOptSel,',',&list2Cnt,1);
2064: if(list1Cnt>list2Cnt) list1Cnt=list2Cnt;
2065: for(j=0; j<list1Cnt; j++){
2066: mssWriteXmlIndent(2,fpw);
2067: xmlTag=mssInitXmlTag("fieldOption",NULL);
2068: mssAddXmlTagAttributeInt(xmlTag,"no" , j+1,NULL);
2069: mssAddXmlTagAttributeStr(xmlTag,"keyword", *(list2+j),NULL);
2070: mssWriteXmlStartTag(xmlTag,NULL,fpw);
2071: mssWriteXmlContent(*(list1+j),NULL,fpw);
2072: mssWriteXmlEndTag(xmlTag,NULL,fpw);
2073: mssWriteRet(fpw);
2074: mssFreeXmlTag(xmlTag);
2075: }
2076: mssFree(*list1); mssFree(list1);
2077: mssFree(*list2); mssFree(list2);
2078: }
2079: break;
2080:
2081: case OKEY:
2082: optKEY=(MssOptKEY *)opt[i];
2083: mssWriteXmlTagStr(2,"type" ,"KEY" ,1,NULL,fpw);
2084: mssWriteXmlTagFlg(2,"mandatory",optKEY->must ,1,NULL,fpw);
2085: mssWriteXmlTagInt(2,"default" ,optKEY->def ,1,NULL,fpw);
2086: mssWriteXmlTagInt(2,"maxCnt" ,optKEY->maxCnt ,1,NULL,fpw);
2087: mssWriteXmlTagStr(2,"inKeyword",optKEY->inKeyWord,1,NULL,fpw);
2088: mssWriteXmlTagStr(2,"title" ,optKEY->title ,1,NULL,fpw);
2089: mssWriteXmlTagStr(2,"comment" ,optKEY->comment ,1,NULL,fpw);
2090: break;
2091:
2092: case OINF:
2093: optINF=(MssOptINF *)opt[i];
2094: mssWriteXmlTagStr(2,"type" ,"INF" ,1,NULL,fpw);
2095: mssWriteXmlTagFlg(2,"mandatory",optINF->must ,1,NULL,fpw);
2096: mssWriteXmlTagInt(2,"maxCnt" ,optINF->maxCnt ,1,NULL,fpw);
2097: mssWriteXmlTagStr(2,"inout" ,"in" ,1,NULL,fpw);
2098: mssWriteXmlTagStr(2,"title" ,optINF->title ,1,NULL,fpw);
2099: mssWriteXmlTagStr(2,"comment" ,optINF->comment ,1,NULL,fpw);
2100: break;
2101:
2102: case OOTF:
2103: optOTF=(MssOptOTF *)opt[i];
2104: mssWriteXmlTagStr(2,"type" ,"OTF" ,1,NULL,fpw);
2105: mssWriteXmlTagFlg(2,"mandatory",optOTF->must ,1,NULL,fpw);
2106: mssWriteXmlTagStr(2,"inout" ,"out" ,1,NULL,fpw);
2107: mssWriteXmlTagStr(2,"title" ,optOTF->title ,1,NULL,fpw);
2108: mssWriteXmlTagStr(2,"comment" ,optOTF->comment ,1,NULL,fpw);
2109: break;
2110:
2111: case OFLG:
2112: optFLG=(MssOptFLG *)opt[i];
2113: mssWriteXmlTagStr(2,"type" ,"FLG" ,1,NULL,fpw);
2114: mssWriteXmlTagStr(2,"title" ,optFLG->title ,1,NULL,fpw);
2115: mssWriteXmlTagStr(2,"comment" ,optFLG->comment ,1,NULL,fpw);
2116: break;
2117: }
2118: /* </option> */
2119: mssWriteXmlIndent(1,fpw);
2120: mssWriteXmlEndTag(optionTag,NULL,fpw);
2121: mssWriteRet(fpw);
2122: mssFreeXmlTag(optionTag);
2123: }
2124: /* </command> */
2125: mssWriteXmlEndTag(commandTag,NULL,fpw);
2126: mssFreeXmlTag(commandTag);
2127: mssWriteRet(fpw);
2128: }
2129:
2130: /**
2131: * # FUNCTION #
2132: * コマンドヘルプドキュメントを出力する。
2133: * 第一パラメータの記号により以下に示す3種類のドキュメントを出力する。
2134: * -h : 簡易ヘルプの表示
2135: * -x : XMLドキュメントによる表示
2136: * -X : manドキュメント(troff)による表示
2137: */
2138: void mssHelpDoc(void *opt[],struct mssComHelp *comHelp, int argc, char **argv)
2139: {
2140:
2141: if( argc>1 ){
2142: if( 0==strncmp(argv[1],"-h",2) ){
2143: prnComHlp(opt,comHelp);
2144: exit(EXIT_FAILURE);
2145: }
2146: if( 0==strncmp(argv[1],"-x",2) ){
2147: prnComXml(opt,comHelp);
2148: exit(EXIT_FAILURE);
2149: }
2150: if( 0==strncmp(argv[1],"-X",2) ){
2151: prnMan(opt,comHelp);
2152: exit(EXIT_FAILURE);
2153: }
2154: }
2155: }
2156:
2157: /**
2158: * # FUNCTION #
2159: * optFldのi番目の項目に項目オプションcが指定されているかどうかを返す。
2160: * ex)
2161: * "-k 日付%nr"の時、c=='r'もしくはc=='n'の時1を返し、それ以外の時0を返す。
2162: */
2163: int mssIsFldOptOn(MssOptFLD *optFld,int i, char c )
2164: {
2165:
2166: if(optFld==NULL) return(0);
2167: if(optFld->fldOpt==NULL) return(0);
2168: if(*(optFld->fldOpt+i)==NULL) return(0);
2169: if( NULL == strchr(*(optFld->fldOpt+i),c) ) return(0);
2170:
2171: return(1);
2172: }
2173:
2174: /**
2175: * # FUNCTION #
2176: * キー項目オプション構造体(MssOptKEY)のstr以下の情報を実体としてコピーする。
2177: */
2178: void mssCpyOptKey(MssOptKEY *to,MssOptKEY *from)
2179: {
2180: int i;
2181:
2182: to->str=mssStrdup(from->str);
2183: /*初期化*/
2184: to->diffSame=from->diffSame;
2185: to->cnt =from->cnt;
2186:
2187: if(to->cnt==0){
2188: to->nam =NULL;
2189: }else{
2190: to->nam =mssMalloc(sizeof(char *)*to->cnt,"cpyOptKey");
2191:
2192: for(i=0; i<to->cnt; i++){
2193: if( *(from->nam +i)!=NULL ) *(to->nam +i)=mssStrdup(*(from->nam +i));
2194: }
2195: }
2196: }
2197:
2198: /**
2199: * # FUNCTION #
2200: * 与えられた数値(val)が数値範囲構造体の範囲にあれば1を返し、
2201: * そうでなければ0を返す。
2202: */
2203: int mssIsInRange(MssOptRNG *optRNG,int val)
2204: {
2205: int i;
2206:
2207: for(i=0; i<optRNG->cnt; i++){
2208: if( *(optRNG->from+i) <= val && val<=*(optRNG->to+i) ) return(1);
2209: }
2210: return(0);
2211: }
2212: