load("myhelpers.mac");

assume(c>0);
assume(%mu>0);
assume(%epsilon>0);
assume(epsinv>0);
assume(muinv>0);

/* A hyperbolic system matrix resulting from a curl */
curlmat(coord):=genmatrix(
  lambda ([i,j], levi_civita([coord,j,i])),
  3,3);

max_submat(i):=blockmat(
  zeromatrix(3,3),
  -epsinv*curlmat(i), /* epsinv = 1/epsilon */
  muinv*curlmat(i), /* muinv = 1/mu */
  zeromatrix(3,3)
  );

n:[nx,ny,nz];

max_Asimp:sum(n[i]*max_submat(i),i,1,3);
max_A:subst([epsinv=1/%epsilon,muinv=1/%mu], max_Asimp);

max_invsubst(x):=subst([epsinv=1/%epsilon, muinv=1/%mu], x);

[max_V, max_D, max_invV]:max_invsubst(hypdiagonalize(max_Asimp));

max_Em:makelist(Em[i],i,1,3);
max_Ep:makelist(Ep[i],i,1,3);
max_Hm:makelist(Hm[i],i,1,3);
max_Hp:makelist(Hp[i],i,1,3);
max_wm:vstack(max_Em,max_Hm);
max_wp:vstack(max_Ep,max_Hp);

max_sm:makelist(sm[i],i,1,6);
max_sp:makelist(sp[i],i,1,6);

max_sminw:hypsimp(max_invV.max_wm);
max_spinw:hypsimp(max_invV.max_wp);

max_wmins:hypsimp(max_V.max_sm);
max_wpins:hypsimp(max_V.max_sp);

max_Emins:makelist(max_wmins[i,1],i,1,3);
max_Hmins:makelist(max_wmins[i,1],i,4,6);

/* ------------------------------------------------------------------------- */
/* Boundary conditions */
/* ------------------------------------------------------------------------- */
max_pecbdrywp:append(-max_Em,max_Hm);

/* ------------------------------------------------------------------------- */
/* Rankine-Hugoniot flux */
/* ------------------------------------------------------------------------- */

max_Dinc:subst([1/(sqrt(%epsilon)*sqrt(%mu))=c], max_D);
max_sflux:hyp_upwind_flux([-c,0,c], max_Dinc);

/* FIXME: max_V should not depend on epsilon and mu, but it does 
   For now, make cp and cm equal. */

max_sflux:subst(
  [cp=1/(sqrt(%epsilon)*sqrt(%mu)), cm=1/(sqrt(%epsilon)*sqrt(%mu))], 
  max_sflux);

max_wflux:fullhypsimp(max_V.ev(max_sflux, [sm=max_sminw,sp=max_spinw]));

max_stronglocalpart:max_A.max_wm;

max_strongwflux:max_stronglocalpart-max_wflux;

/* ------------------------------------------------------------------------- */
/* vector components */
/* ------------------------------------------------------------------------- */

normalcomp(v):=(v.n)*n;
tangentialcomp(v):=v-normalcomp(v);
