/*------------------------->  Sather - configfile  <-------------------------*/
/* Copyright (C) 2000 by K Hopper, University of Waikato, New Zealand        */
/* This file is part of the GNU Sather library. It is free software; you may */
/* redistribute  and/or modify it under the terms of the GNU Library General */
/* Public  License (LGPL)  as published  by the  Free  Software  Foundation; */
/* either version 2 of the license, or (at your option) any later version.   */
/* This  library  is distributed  in the  hope that it will  be  useful, but */
/* WITHOUT ANY WARRANTY without even the implied warranty of MERCHANTABILITY */
/* or FITNESS FOR A PARTICULAR PURPOSE. See Doc/LGPL for more details.       */
/* The license text is also available from:  Free Software Foundation, Inc., */
/* 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA                     */
/*------------>  Please email comments to <bug-sather@gnu.org>  <------------*/

#ifndef AREF_CONFIG
#define AREF_CONFIG

#ifdef PP
#undef PP
#endif

#define PP	no_pre,no_post

AREF_ASIZE:			PP,reads "@0::asize",
				attr_access 1,
				var "@r $$;",exec "$$=ASIZE(@(0)$0);" "$$",
				f_var "@r $$;",f_exec "if(^0) $$=ASIZE(@(0)$0); else READASIZE($$,@0,$0);" "$$";

AREF_AGET:		 	PP,reads "@0::[]" "@0::asize",
				attr_access 1 0 0,
				var "@r $$;",
				exec "$$=@(r)ARR(@(0)$0,$1);" "$$",
				f_exec "#if %r==0"   "\tif(^0) $$=@(r)ARR(@(0)$0,$1); else F_R_RARR_NA($$,@0,$0,$1);" 
				       "#elif %r==1" "\tif(^0) $$=@(r)ARR(@(0)$0,$1); else F_VA_RARR_NA($$,@0,$0,$1);" 
				       "#elif %r==2" "\tif(^0) VASS_LP($$,@r,ARR(@(0)$0,$1)); else F_V_RARR_LP(@r,$$,@0,$0,$1);" 
				       "#endif" "$$";

AREF_ASET:			PP,writes "@0::[]",reads "@0::asize",
				attr_access 1 0 0,
				exec "SARR(@(0)$0,$1,@(2)$2);",
				f_exec "#if %2==0" "\tif(^0) SARR(@(0)$0,$1,@(2)$2); else F_R_WARR_NA(@0,$0,$1,$2);" 
				       "#elif %2==1" "\tif(^0) SARR(@(0)$0,$1,@(2)$2); else F_VA_WARR_NA(@0,$0,$1,$2);" 
				       "#elif %2==2" "\tif(^0) { CHK_BOUNDS($1,0,ASIZE($0)-1,0);VASS_PP((@(0)$0)->arr_part[$1],@2,$2);} else F_V_WARR_LP(@0,$0,$1,@2,$2);" 
				       "#endif";
AREF_ACLEAR:			PP,writes "@0::[],@0::asize",
				attr_access 1,
				 -- about as expensive as one access in pSather
				exec "AREFACLEAR($0);",
				f_exec "if(^0) AREFACLEAR($0); else F_AREFACLEAR_A(@0,$0);";

AREF_ACOPY:			PP,reads "@0::[]" "@0::asize",writes "@0::[]" "@0::asize",
				attr_access 5 5,
				exec "AREFACOPY($0,$1);",
				f_exec "if(^0 && ^1) AREFACOPY($0,$1); else F_AREFACOPY_AA(@0,@P0,$0,$1);";

AREF_ACOPY_BEG:			PP,reads "@0::[]" "@0::asize",writes "@0::[]" "@0::asize",
				attr_access 5 0 5,
				exec "AREFACOPYB($0,$1,$2);",
				f_exec "if(^0 && ^2) AREFACOPYB($0,$1,$2); else F_AREFACOPYB_AA(@0,@P0,$0,$1,$2);";

AREF_ACOPY_BEG_NUM:		PP,reads "@0::[]" "@0::asize",writes "@0::[]" "@0::asize",
				attr_access 5 0 0 5,
				exec "AREFACOPYBN($0,$1,$2,$3);",
				f_exec "if(^0 && ^3) AREFACOPYBN($0,$1,$2,$3); else F_AREFACOPYBN_AA(@0,@P0,$0,$1,$2,$3);";

AREF_ACOPY_BEG_NUM_SRCBEG:	PP,reads "@0::[]" "@0::asize",writes "@0::[]" "@0::asize",
				attr_access 5 0 0 0 5,
				exec "AREFACOPYBNS($0,$1,$2,$3,$4);",
				f_exec "if(^0 && ^4) AREFACOPYBNS($0,$1,$2,$3,$4); else F_AREFACOPYBNS_AA(@0,@P0,$0,$1,$2,$3,$4);";

AREF_AELTB:			reads  "@0::[]" "@0::asize",
				attr_access 1,
				var    "INT $$br;",
				init   "$$br=ASIZE(@(0)$0);",
				break  "$$br",
				temp   "@r a$$;",
				iter   "a$$=ARR(@(0)$0,$#);" "a$$",
				f_init "if(^0) $$br=ASIZE(@(0)$0); else $$br=F_ASIZE(@0,$0);",
				f_iter "#if %r==0" "if(^0) a$$=ARR(@(0)$0,$#); else F_R_RARR_NA(a$$,@0,$0,$#);" 
				       "#elif %r==1" "if(^0) a$$=ARR(@(0)$0,$#); else F_VA_RARR_NA(a$$,@0,$0,$#);" 
				       "#elif %r==2" "if(^0) VASS_LP(a$$,@r,ARR(@(0)$0,$#)); else F_V_RARR_LP(@r,a$$,@0,$0,$#);" 
				       "#endif" "a$$";

AREF_AELT_BEGB:			reads  "@0::[]" "@0::asize",
				attr_access 1 0,
				var    "INT $$c,$$s;",
				temp   "@r a$$;",
				init   "$$c=$1-1;$$s=ASIZE(@(0)$0);",
				f_init "$$c=$1-1;$$s=F_ASIZE(@0,$0);",
				iter   "if(++$$c>=$$s) @@;"
				       "a$$=ARR(@(0)$0,$$c);" "a$$",
				f_iter "if(++$$c>=$$s) @@;"
				       "#if %r==0" "if(^0) a$$=ARR(@(0)$0,$$c); else F_R_RARR_NA(a$$,@0,$0,$$c);" 
				       "#elif %r==1" "if(^0) a$$=ARR(@(0)$0,$$c); else F_VA_RARR_NA(a$$,@0,$0,$$c);" 
				       "#elif %r==2" "if(^0) VASS_LP(a$$,@r,ARR(@(0)$0,$#)); else F_V_RARR_LP(@r,a$$,@0,$0,$#);" 
				       "#endif" "a$$";

AREF_AELT_BEG_NUMB:		reads  "@0::[]" "@0::asize",
				attr_access 1 0 0,
				var    "INT $$c,$$m;",
				temp   "@r a$$;",
				init   "$$c=$1-1;$$m=$1+$2;",
				iter   "if(++$$c>=$$m) @@;"
				       "a$$=ARR(@(0)$0,$$c);" "a$$",
				f_iter "if(++$$c>=$$m) @@;"
				       "#if %r==0" "if(^0) a$$=ARR(@(0)$0,$$c); else F_R_RARR_NA(a$$,@0,$0,$$c);" 
				       "#elif %r==1" "if(^0) a$$=ARR(@(0)$0,$$c); else F_VA_RARR_NA(a$$,@0,$0,$$c);" 
				       "#elif %r==2" "if(^0) VASS_LP(a$$,@r,ARR(@(0)$0,$#)); else F_V_RARR_LP(@r,a$$,@0,$0,$#);" 
				       "#endif"
				       "a$$";

AREF_AELT_BEG_NUM_STEPB:	reads  "@0::[]" "@0::asize",
				attr_access 1 0 0 0,
				var    "INT $$c,$$m;",
				temp   "@r a$$;",
				init   "$$c=$1;$$m=$1+$2*$3;",
				iter   "if($3>=0&&$$c>=$$m||$3<0&&$$c<=$$m) @@;"
				       "a$$=ARR(@(0)$0,$$c);" "$$c+=$3;" "a$$",
				f_iter "if($$c>=$$m) @@;"
				       "#if %r==0" "if(^0) a$$=ARR(@(0)$0,$$c); else F_R_RARR_NA(a$$,@0,$0,$$c);" 
				       "#elif %r==1" "if(^0) a$$=ARR(@(0)$0,$$c); else F_VA_RARR_NA(a$$,@0,$0,$$c);" 
				       "#elif %r==2" "if(^0) VASS_LP(a$$,@r,ARR(@(0)$0,$#)); else F_V_RARR_LP(@r,a$$,@0,$0,$#);" 
				       "#endif" "$$c+=$3;" "a$$";

AREF_ASETB:			writes "@0::[]",
				attr_access 1,
				reads  "@0::asize",
				var    "INT $$br;",
				init   "$$br=ASIZE(@(0)$0);",
				f_init "$$br=F_ASIZE(@0,$0);",
				break  "$$br",
				iter   "SARR(@(0)$0,$#,@(1)$1);",
				f_iter "#if %1==0" "if(^0) SARR(@(0)$0,$#,@(1)$1); else F_R_WARR_NA(@0,$0,$#,$1);" 
				       "#elif %1==1" "if(^0) SARR(@(0)$0,$#,@(1)$1); else F_VA_WARR_NA(@0,$0,$#,$1);" 
				       "#elif %1==2" "if(^0) { CHK_BOUNDS($#,0,ASIZE($0)-1,0);VASS_PP((@(0)$0)->arr_part[$#],@1,$1);} else F_V_WARR_LP(@0,$0,$#,@1,$1);" 
				       "#endif";

AREF_ASET_BEGB:			writes "@0::[]",
				reads  "@0::asize",
				attr_access 1 0,
				var    "INT $$c,$$s;",
				init   "$$c=$1-1;$$s=ASIZE(@(0)$0);",
				f_init "$$c=$1-1;$$s=F_ASIZE(@0,$0);",
				iter   "if(++$$c>=$$s) @@;"
				       "SARR(@(0)$0,$$c,@(2)$2);",
				f_iter "if(++$$c>=$$s) @@;"
				       "#if %2==0" "if(^0) SARR(@(0)$0,$$c,@(2)$2); else F_R_WARR_NA(@0,$0,$$c,$2);" 
				       "#elif %2==1" "if(^0) SARR(@(0)$0,$$c,@(2)$2); else F_VA_WARR_NA(@0,$0,$$c,$2);" 
				       "#elif %2==2" "if(^0) { CHK_BOUNDS($$c,0,ASIZE($0)-1,0);VASS_PP((@(0)$0)->arr_part[$$c],@2,$2);} else F_V_WARR_LP(@0,$0,$$c,@2,$2);" 
				       "#endif";

AREF_ASET_BEG_NUMB:		writes "@0::[]",
				reads  "@0::asize",
				attr_access 1 0 0,
				var    "INT $$c,$$m;",
				init   "$$c=$1-1;$$m=$1+$2;",
				iter   "if(++$$c>=$$m) @@;"
				       "SARR(@(0)$0,$$c,@(3)$3);",
				f_iter "if(++$$c>=$$m) @@;"
				       "#if %3==0" "if(^0) SARR(@(0)$0,$$c,@(1)$3); else F_R_WARR_NA(@0,$0,$$c,$3);" 
				       "#elif %3==1" "if(^0) SARR(@(0)$0,$$c,@(1)$3); else F_VA_WARR_NA(@0,$0,$$c,$3);" 
				       "#elif %3==2" "if(^0) { CHK_BOUNDS($$c,0,ASIZE($0)-1,0);VASS_PP((@(0)$0)->arr_part[$$c],@3,$3);} else F_V_WARR_LP(@0,$0,$$c,@3,$3);" 
				       "#endif";

AREF_ASET_BEG_NUM_STEPB:	reads  "@0::[]",
				writes "@0::asize",
				attr_access 1 0 0 0,
				var    "INT $$c,$$m;",
				init   "$$c=$1;$$m=$1+$2*$3;",
				iter   "if($$c>=$$m) @@;"
				       "SARR(@(0)$0,$$c,@(4)$4);" "$$c+=$3;",
				f_iter "if($$c>=$$m) @@;"
				       "#if %4==0" "if(^0) SARR(@(0)$0,$$c,@(1)$4); else F_R_WARR_NA(@0,$0,$$c,$4);" 
				       "#elif %4==1" "if(^0) SARR(@(0)$0,$$c,@(1)$4); else F_VA_WARR_NA(@0,$0,$$c,$4);" 
				       "#elif %4==2" "if(^0) { CHK_BOUNDS($$c,0,ASIZE($0)-1,0);VASS_PP((@(0)$0)->arr_part[$$c],@4,$4);} else F_V_WARR_LP(@0,$0,$$c,@4,$4);" 
				       "#endif" "$$c+=$3;";

AREF_AINDB:			reads  "@0::asize",
				attr_access 0,
				var    "INT $$br;",
				init   "$$br=ASIZE(@(0)$0);",
				f_init "if(^0) $$br=ASIZE(@(0)$0); else $$br=F_ASIZE(@0,$0);",
				break  "$$br",
				temp   "@r r$$;",
				iter   "r$$=$#;" "r$$";

AREF_ARRAY_PTR:			exec   "(void *)$0->arr_part";

#endif
