#include "pdeov_decl.h"

void foo (
          Env &env)
{
  int pe=env.pre.pe;
  Alias(PartOne,ALL1,env.pre.ALL1);
  Alias(PartOne,ONE1,env.pre.ONE1);
  Alias(PartNP,ALLn,env.pre.ALLn);
  Alias(PartNP,ONEn,env.pre.ONEn);
  Alias(PartNP,PPEn,env.pre.PPEn);
  Alias(PartRange2D,cell,env.cell);
  Alias(PartRange2D,cell2,env.cell2);
  Alias(PartRange2D,halom,env.halom);
  Alias(PartRange2D,halo,env.halo);
  Alias(PartRange2D,fullone,env.fullone);
  Alias(MPartRange2D,boundary,env.boundary);
  Alias(MPartRange2D,border,env.border);
  Alias(SwapRange2D,sw_chm,env.sw_chm);
  Alias(SwapRange2D,sw_ca,env.sw_ca);
  Alias(Config,cfg,env.cfg);
  Alias(File,fout,env.fout);

  Data (Int, cond); Data (Int, idx); 
  DataRa (Vector2Dreal, A_fullone, fullone[pe]); DataRa (Vector2Dreal, A_halo, halo[pe]); 
  DataRa (Vector2Dreal, BD_halo, halo[pe]); DataRa (Vector2Dreal, B_halo, halo[pe]); 

  matrix_read (cfg, cell[pe], halo[pe], A_halo, BD_halo);

  for (int _mi=0; _mi<boundary.getNo(pe); _mi++)
      copy (BD_halo, boundary.idx(pe,_mi), A_halo, boundary.idx(pe,_mi));

  for (int _mi=0; _mi<boundary.getNo(pe); _mi++)
      copy (BD_halo, boundary.idx(pe,_mi), B_halo, boundary.idx(pe,_mi));

  CLK_MAIN_LP_BEGIN;

  for (idx=0, cond=1; cond; idx++)
  {
      CLK_MAIN_BEGIN(idx);

      swapBegin (sw_chm, A_halo, A_halo, 0, pe);

      ftcs_step (cfg, A_halo, cell[pe], cell2[pe], B_halo);

      econd (cfg, idx, cond);

      swapEnd (sw_chm, A_halo, A_halo, 0, pe);

      for (int _mi=0; _mi<border.getNo(pe); _mi++)
      {
          ftcs_step (cfg, A_halo, halo[pe], border.idx(pe,_mi), B_halo);
      }

      swapBegin (sw_chm, B_halo, B_halo, 0, pe);

      ftcs_step (cfg, B_halo, cell[pe], cell2[pe], A_halo);

      swapEnd (sw_chm, B_halo, B_halo, 0, pe);

      for (int _mi=0; _mi<border.getNo(pe); _mi++)
      {
          ftcs_step (cfg, B_halo, halo[pe], border.idx(pe,_mi), A_halo);
      }

      CLK_MAIN_END(idx);
  }

  CLK_MAIN_LP_END;

  swapBegin (sw_ca, A_halo, A_fullone, 0, pe);

  swapEnd (sw_ca, A_halo, A_fullone, 0, pe);

  Print (fout, A_fullone, fullone[pe]);

  check_sym (A_fullone, fullone[pe]);
}


