static    char    sccsid[]="%Z% %M% %I% %E% %U%";
/************************************************************************/
/*																		*/
/*	処理目的	： ＥＬＳＥＩＦコマンドメイン							*/
/*																		*/
/*	関数名		： int cl_process_else_if(pLeaf, pProc)					*/
/*																		*/
/*	引き数		： (I)Leaf		: * pLeaf								*/
/*				   (I)ProcCT	: * pProc								*/
/*																		*/
/*	戻り値		： ERROR												*/
/*				   NORMAL												*/
/*																		*/
/*	処理概要	：														*/
/*																		*/
/************************************************************************/

#include "colmn.h"

extern GlobalCt *pGlobTable;

static char sep[]={" \t'+-*/&|=^~!<>[](),;"};

int cl_process_else_if(pLeaf, pProc)
Leaf   *pLeaf;
ProcCT *pProc;
{
	int rc,id;
	BlockCB *pIfCB,*pBlockCB;

	if (!(pIfCB = pProc->pcrBlockCB)) return -1;
	id = pIfCB->cid;
	if (id != C_IF) return -1;

	if (pIfCB->ElseFlag == L_ON) {
		ERROROUT1(FORMAT(368),"ELSE");	/* 前に ELSE があります。 */
		return ECL_EX_ELSEIF;
	}

	if (pIfCB->TureFlag == L_ON) {
		pProc->Nextleaf = pLeaf->rightleaf;
		return 0;
	}
	if ((rc = cl_if_comp_ctl(pLeaf,pProc)) < NORMAL) return ECL_EX_IF;

	if (rc == L_ON) {
		pIfCB->TureFlag = L_ON;
		pProc->Nextleaf = pLeaf->leftleaf;
DEBUGOUTL1(200,"cl_process_else_if: push [ %s ]",cl_get_pcmd_line(pLeaf->rightleaf));
		cl_ret_leaf_push(pProc,pLeaf->rightleaf);
	}
	else {
		pProc->Nextleaf = pLeaf->rightleaf;
	}

	return 0;
}

/********************************/
/*								*/
/********************************/
static int _mk_exp(swParm,nparm,prmp,mcat)
char *swParm;
int  nparm;
parmList  *prmp[];
MCAT *mcat;
{
	char *line;
	int line_len;
	SSPL_S ssp;
	int rc,i,len,lpar1,lpar2,atr0,atr,flag;
	char wrk[256],*p,c;

	ssp.sp = 0;
	ssp.wd = wrk;
	ssp.wdmax = sizeof(wrk);
	line = prmp[0]->prp;
	line_len = prmp[0]->prmlen;
	mcat->mc_ipos = 0;
	if (mcat->mc_bufp) *mcat->mc_bufp = '\0';
	len = strlen(swParm);
	akxtmcat(mcat,swParm,len);
	flag = 0;
	while ((rc=akxtgwnsl(line,line_len,&ssp,sep,1)) > 0) {
		if (flag) {
			akxtmcats(mcat,")||");
			akxtmcat(mcat,swParm,len);
		}
		lpar1 = lpar2 = 0;
		if (cl_gx_is_operator(wrk,COMP) ||
		    !stricmp(wrk,"LIKE") || !stricmp(wrk,"iLIKE")) ;
		else {
			akxtmcats(mcat,"==");
			if ((c=*wrk) == '(') lpar1 = 1;
			else if (c == '[') lpar2 = 1;
		}
		atr = ssp.attr[0];
		akxtmcats(mcat,wrk);
		while ((rc=akxtgwnsl(line,line_len,&ssp,sep,1)) > 0) {
			atr0 = atr;
			atr  = ssp.attr[0];
			if ((c=*wrk) == '(') lpar1++;
			else if (c == ')') lpar1--;
			else if (c == '[') lpar2++;
			else if (c == ']') lpar2--;
			if (!lpar1 && !lpar2 && c==',') break;
			if (atr0<10 && atr<10) akxtmcats(mcat," ");
			akxtmcat(mcat,wrk,rc);
		}
		if (lpar1 || lpar2) {
			ERROROUT(FORMAT(369));	/* カッコの対応が取れていません。 */
			return -1;
		}
		flag = 1;
	}
	akxtmcats(mcat,")");

DEBUGOUTL1(120,"_mk_exp: buf=[%s]",mcat->mc_bufp);

	return mcat->mc_ipos;
}

/********************************/
/*								*/
/********************************/
int cl_process_case(pLeaf, pProc)
Leaf   *pLeaf;
ProcCT *pProc;
{
	static MCAT mcat={'M','C',256,0,0,0,NULL,0};
	int rc,val,do_compile;
	tdtInfoParm InfoParm,*p;
	GXObject *pbxObj;
	int id;
	BlockCB *pIfCB;

	if (!(pIfCB = pProc->pcrBlockCB)) return -1;
	id = pIfCB->cid;

DEBUGOUTL4(110,"cl_process_case: Enter pIfCB=%08x id=%08x %s TureFlag=%08x",pIfCB,id,cl_gets_cmd_name(id),pIfCB->TureFlag);

	if (id != C_SWITCH) return -1;
#if 0	/* 2017.03.18 */
	if (pIfCB->ElseFlag == L_ON) {
		ERROROUT1(FORMAT(368),"DEFAULT");	/* 前に DEFAULT があります。 */
		return ECL_EX_ELSEIF;
	}
#endif
	if (pIfCB->TureFlag == L_ON) {
#if 1
		if (pIfCB->iLoopMax != C_BREAK) {
			pIfCB->Blockleaf = pLeaf->rightleaf;	/* Add 2019.11.02 */
			pProc->Nextleaf = pLeaf->leftleaf;

DEBUGOUTL1(110,"cl_process_case: push [ %s ]",cl_get_pcmd_line(pLeaf->rightleaf));

			cl_ret_leaf_push(pProc,pLeaf->rightleaf);
		}
		else
			pProc->Nextleaf = pLeaf->rightleaf;
#else
		pProc->Nextleaf = pLeaf->rightleaf;
#endif
		return 0;
	}

	do_compile = 1;
	if (pbxObj=pLeaf->cmd.prmp[0]->bxobj) {
		if (pbxObj->nobj > 0) do_compile = 0;
	}
	if (do_compile) {
		rc = _mk_exp(pIfCB->pSwParm,pLeaf->cmd.prmnum,pLeaf->cmd.prmp,&mcat);
		if (rc < 0) return rc;
	}
	rc = cl_gx_expsn_obj_opt(mcat.mc_bufp,rc,&(pLeaf->cmd.prmp[0]->bxobj),pProc->Obj,&InfoParm,0);
	if (rc < 0) return rc;
	if (InfoParm.pi_pos) {
		pIfCB->iUsed = D_SWITCH_CASE;	/* Add 2017.3.25 */
		pIfCB->TureFlag = L_ON;
		pIfCB->Blockleaf = pLeaf->rightleaf;	/* Add 2017.3.25 */
		pProc->Nextleaf = pLeaf->leftleaf;

DEBUGOUTL1(110,"cl_process_case: push [ %s ]",cl_get_pcmd_line(pLeaf->rightleaf));

		cl_ret_leaf_push(pProc,pLeaf->rightleaf);
	}
	else {
		pProc->Nextleaf = pLeaf->rightleaf;
	}

	return 0;
}

/********************************/
/*								*/
/********************************/
static int _mk_exp_exception(nparm,prmp,mcat)
int  nparm;
parmList  *prmp[];
MCAT *mcat;
{
	char *line;
	int line_len;
	SSPL_S ssp;
	int rc,len,flag,val;
	char wrk[256],*p,buf[16];
	tdtException *ep;

	ssp.sp = 0;
	ssp.wd = wrk;
	ssp.wdmax = sizeof(wrk);
	line = prmp[0]->prp;
	line_len = prmp[0]->prmlen;
	mcat->mc_ipos = 0;
	if (mcat->mc_bufp) *mcat->mc_bufp = '\0';

	akxtmcats(mcat,"(($EXCEPTION");
	flag = 0;
	while ((rc=akxtgwnsl(line,line_len,&ssp,sep,1)) > 0) {
		if (flag) {
			akxtmcats(mcat,")||");
			akxtmcats(mcat,"(($EXCEPTION");
		}
		if (ep=cl_get_exception_name(wrk,rc,0)) {
			val = ep->id;
			sprintf(buf,"0x%08x",val);
			if (!(val & 0x7fffffff)) p = "0x80000000";
			else if (!(val & 0x00ffffff)) p = "0xff000000";
			else if (!(val & 0x0000ffff)) p = "0xffff0000";
			else p = NULL;
			if (p) sprintf(wrk," & %s)==%s",p,buf);
			else sprintf(wrk,"==%s)",buf);
			akxtmcats(mcat,wrk);
		}
		else return -100;
		if ((rc=akxtgwnsl(line,line_len,&ssp,sep,1)) > 0) {
			if (*wrk != ',') return -100;
		}
		else break;
		flag = 1;
	}
	akxtmcats(mcat,")");

DEBUGOUTL1(120,"_mk_exp_exception: buf=[%s]",mcat->mc_bufp);

	return mcat->mc_ipos;
}

/********************************/
/*								*/
/********************************/
int cl_process_catch(pLeaf, pProc)
Leaf   *pLeaf;
ProcCT *pProc;
{
	static MCAT mcat={'M','C',256,0,0,0,NULL,0};
	int rc,val,do_compile;
	tdtInfoParm InfoParm,*p;
	GXObject *pbxObj;
	int id;
	BlockCB *pIfCB;

	if (!(pIfCB = pProc->pcrBlockCB)) return -1;
	id = pIfCB->cid;
	if (id != C_TRY) return -1;

	if (pIfCB->ElseFlag == L_ON) {
		ERROROUT1(FORMAT(368),"FINALL");	/* 前に FINALL があります。 */
		return ECL_EX_ELSEIF;
	}

	if (pIfCB->TureFlag == L_ON) {	/* no exceptions */
		pProc->Nextleaf = pLeaf->rightleaf;
		return 0;
	}

	rc = 0;
	if (pLeaf->cmd.prmnum > 0) {
		do_compile = 1;
		if (pbxObj=pLeaf->cmd.prmp[0]->bxobj) {
			if (pbxObj->nobj > 0) do_compile = 0;
		}
		if (do_compile) {
			if ((rc=_mk_exp_exception(pLeaf->cmd.prmnum,pLeaf->cmd.prmp,&mcat)) == -100)
				rc = _mk_exp("($EXCEPTION",pLeaf->cmd.prmnum,pLeaf->cmd.prmp,&mcat);
		}
		if (rc >= 0)
			rc = cl_gx_expsn_obj_opt(mcat.mc_bufp,rc,&(pLeaf->cmd.prmp[0]->bxobj),pProc->Obj,&InfoParm,0);
		if (rc < 0) {
			InfoParm.pi_pos = 1;
			pGlobTable->exception = ETC_EXCEPTION;
		}
	}
	else InfoParm.pi_pos = 1;

	if (InfoParm.pi_pos) {
		pIfCB->TureFlag = L_ON;
		pProc->Nextleaf = pLeaf->leftleaf;
DEBUGOUTL1(200,"cl_process_catch: push [ %s ]",cl_get_pcmd_line(pLeaf->rightleaf));
		cl_ret_leaf_push(pProc,pLeaf->rightleaf);
	}
	else {
		pProc->Nextleaf = pLeaf->rightleaf;
	}

	return rc;
}
