// Alternatively, this file may be used under the terms of Open CASCADE
 // commercial license or contractual agreement.
 
-#include <BndLib.ixx> // BUG BUG BUG pas .hxx
+#include <BndLib.ixx>
 
 #include <ElCLib.hxx>
 #include <gp_XYZ.hxx>
 #include <gp_XY.hxx>
 #include <gp_Pnt.hxx>
 #include <gp_Pnt2d.hxx>
-#include <BndLib_Compute.hxx>
 #include <Precision.hxx>
 #include <Standard_Failure.hxx>
 
+namespace
+{
+  //! Compute method
+  template<class PointType, class BndBoxType>
+  void Compute (const Standard_Real theP1, const Standard_Real theP2,
+                const Standard_Real theRa ,const Standard_Real theRb,
+                const PointType& theXd, const PointType& theYd, const PointType& theO,
+                BndBoxType& theB)
+  {
+    Standard_Real aTeta1;
+    Standard_Real aTeta2;
+    if(theP2 < theP1)
+    { 
+      aTeta1 = theP2;
+      aTeta2 = theP1;
+    }
+    else
+    {
+      aTeta1 = theP1;
+      aTeta2 = theP2;
+    }
+
+    Standard_Real aDelta = Abs(aTeta2-aTeta1); 
+    if(aDelta > 2. * M_PI)
+    {
+      aTeta1 = 0.;
+      aTeta2 = 2. * M_PI;
+    }
+    else
+    {
+      if(aTeta1 < 0.)
+      {
+        do{ aTeta1 += 2.*M_PI; } while (aTeta1 < 0.);
+      }
+      else if (aTeta1 > 2.*M_PI)
+      {
+        do { aTeta1 -= 2.*M_PI; } while (aTeta1 > 2.*M_PI);
+      }
+      aTeta2 = aTeta1 + aDelta;
+    }
+
+    // One places already both ends
+    Standard_Real aCn1, aSn1 ,aCn2, aSn2;
+    aCn1 = Cos(aTeta1); aSn1 = Sin(aTeta1);
+    aCn2 = Cos(aTeta2); aSn2 = Sin(aTeta2);
+    theB.Add(PointType( theO.Coord() +theRa*aCn1*theXd.Coord() +theRb*aSn1*theYd.Coord()));
+    theB.Add(PointType(theO.Coord() +theRa*aCn2*theXd.Coord() +theRb*aSn2*theYd.Coord()));
+    
+    Standard_Real aRam, aRbm;
+    if (aDelta > M_PI/8.)
+    {
+      // Main radiuses to take into account only 8 points (/cos(Pi/8.))
+      aRam = theRa/0.92387953251128674;
+      aRbm = theRb/0.92387953251128674;
+    }
+    else
+    {
+      // Main radiuses to take into account the arrow
+      Standard_Real aTc = cos(aDelta/2);
+      aRam = theRa/aTc;
+      aRbm = theRb/aTc;
+    }
+    theB.Add(PointType(theO.Coord() + aRam*aCn1*theXd.Coord() + aRbm*aSn1*theYd.Coord()));
+    theB.Add(PointType(theO.Coord() + aRam*aCn2*theXd.Coord() + aRbm*aSn2*theYd.Coord()));
+
+// cos or sin M_PI/4.
+#define PI4 0.70710678118654746
+
+// 8 points of the polygon
+#define addPoint0 theB.Add(PointType(theO.Coord() +aRam*theXd.Coord()))
+#define addPoint1 theB.Add(PointType(theO.Coord() +aRam*PI4*theXd.Coord() +aRbm*PI4*theYd.Coord()))
+#define addPoint2 theB.Add(PointType(theO.Coord() +aRbm*theYd.Coord()))
+#define addPoint3 theB.Add(PointType(theO.Coord() -aRam*PI4*theXd.Coord() +aRbm*PI4*theYd.Coord()))
+#define addPoint4 theB.Add(PointType(theO.Coord() -aRam*theXd.Coord() ))
+#define addPoint5 theB.Add(PointType(theO.Coord() -aRam*PI4*theXd.Coord() -aRbm*PI4*theYd.Coord()))
+#define addPoint6 theB.Add(PointType(theO.Coord() -aRbm*theYd.Coord()))
+#define addPoint7 theB.Add(PointType(theO.Coord() +aRam*PI4*theXd.Coord() -aRbm*PI4*theYd.Coord()))
+
+    Standard_Integer aDeb = (Standard_Integer )( aTeta1/(M_PI/4.));
+    Standard_Integer aFin = (Standard_Integer )( aTeta2/(M_PI/4.));
+    aDeb++;
+
+    if (aDeb > aFin) return;
+
+    switch (aDeb)
+    {
+    case 1:
+      {
+        addPoint1;
+        if (aFin <= 1) break;
+      }
+    case 2:
+      {
+        addPoint2;
+        if (aFin <= 2) break;
+      }
+    case 3:
+      {
+        addPoint3;
+        if (aFin <= 3) break;
+      }
+    case 4:
+      {
+        addPoint4;
+        if (aFin <= 4) break;
+      }
+    case 5:
+      {
+        addPoint5;
+        if (aFin <= 5) break;
+      }
+    case 6:
+      {
+        addPoint6;
+        if (aFin <= 6) break;
+      }
+    case 7:
+      {
+        addPoint7;
+        if (aFin <= 7) break;
+      }
+    case 8:
+      {
+        addPoint0;
+        if (aFin <= 8) break;
+      }
+    case 9:
+      {
+        addPoint1;
+        if (aFin <= 9) break;
+      }  
+    case 10:
+      {
+        addPoint2;
+        if (aFin <= 10) break;
+      }
+    case 11:
+      {
+        addPoint3;
+        if (aFin <= 11) break;
+      }  
+    case 12:
+      {
+        addPoint4;
+        if (aFin <= 12) break;
+      }  
+    case 13:
+      {
+        addPoint5;
+        if (aFin <= 13) break;
+      }
+    case 14:
+      {
+        addPoint6;
+        if (aFin <= 14) break;
+      }
+    case 15:
+      {
+        addPoint7;
+        if (aFin <= 15) break;
+      }
+    }
+  }
+} // end namespace
 
 static void OpenMin(const gp_Dir& V,Bnd_Box& B) {
   gp_Dir OX(1.,0.,0.);
                const Standard_Real P2,
                const Standard_Real Tol, Bnd_Box& B) {
 
-  Compute(P1,P2,C.Radius(),C.Radius(),C.XAxis().Direction().XYZ(), 
-           C.YAxis().Direction().XYZ(),C.Location().XYZ(),B);
+      Compute(P1,P2,C.Radius(),C.Radius(),gp_Pnt(C.XAxis().Direction().XYZ()), 
+        gp_Pnt(C.YAxis().Direction().XYZ()),C.Location(),B);
   B.Enlarge(Tol);
 }
 
                 const Standard_Real P2,
                 const Standard_Real Tol, Bnd_Box2d& B) {
 
-  Compute(P1,P2,C.Radius(),C.Radius(),C.XAxis().Direction().XY(),
-           C.YAxis().Direction().XY(),C.Location().XY(),B);
+       Compute(P1,P2,C.Radius(),C.Radius(),gp_Pnt2d(C.XAxis().Direction().XY()),
+         gp_Pnt2d(C.YAxis().Direction().XY()),C.Location(),B);
   B.Enlarge(Tol);
 }
 
                 const Standard_Real P2,
                 const Standard_Real Tol, Bnd_Box& B) {
 
-  Compute(P1,P2,C.MajorRadius(),C.MinorRadius(),C.XAxis().Direction().XYZ(), 
-           C.YAxis().Direction().XYZ(),C.Location().XYZ(),B);
+  Compute(P1,P2,C.MajorRadius(),C.MinorRadius(),gp_Pnt(C.XAxis().Direction().XYZ()), 
+           gp_Pnt(C.YAxis().Direction().XYZ()),C.Location(),B);
   B.Enlarge(Tol);
 }
 
                 const Standard_Real Tol, Bnd_Box2d& B) {
 
   Compute(P1,P2,C.MajorRadius(),C.MinorRadius(),
-         C.XAxis().Direction().XY(),
-         C.YAxis().Direction().XY(),C.Location().XY(),B);
+         gp_Pnt2d(C.XAxis().Direction().XY()),
+         gp_Pnt2d(C.YAxis().Direction().XY()),C.Location(),B);
   B.Enlarge(Tol);
 }
 
     }
     else {
       Compute(UMin,UMax,S.Radius(),S.Radius(),
-             S.XAxis().Direction().XYZ(),
-             S.YAxis().Direction().XYZ(),
-             S.Location().XYZ() + VMax*S.Axis().Direction().XYZ(),B);
+             gp_Pnt(S.XAxis().Direction().XYZ()),
+             gp_Pnt(S.YAxis().Direction().XYZ()),
+             gp_Pnt(S.Location().XYZ() + VMax*S.Axis().Direction().XYZ()),B);
       OpenMin(S.Axis().Direction(),B);
     }
   }
     }
     else {
       Compute(UMin,UMax,S.Radius(),S.Radius(),
-             S.XAxis().Direction().XYZ(),
-             S.YAxis().Direction().XYZ(),
-             S.Location().XYZ() + VMax*S.Axis().Direction().XYZ(),B);
+             gp_Pnt(S.XAxis().Direction().XYZ()),
+             gp_Pnt(S.YAxis().Direction().XYZ()),
+             gp_Pnt(S.Location().XYZ() + VMax*S.Axis().Direction().XYZ()),B);
       OpenMax(S.Axis().Direction(),B);
     }
 
   }
   else {
     Compute(UMin,UMax,S.Radius(),S.Radius(),
-           S.XAxis().Direction().XYZ(),
-           S.YAxis().Direction().XYZ(),
-           S.Location().XYZ() + VMin*S.Axis().Direction().XYZ(),B);
+           gp_Pnt(S.XAxis().Direction().XYZ()),
+           gp_Pnt(S.YAxis().Direction().XYZ()),
+           gp_Pnt(S.Location().XYZ() + VMin*S.Axis().Direction().XYZ()),B);
     if (Precision::IsNegativeInfinite(VMax)) {
       OpenMin(S.Axis().Direction(),B);
     }
     }
     else {
       Compute(UMin,UMax,S.Radius(),S.Radius(),
-             S.XAxis().Direction().XYZ(),
-             S.YAxis().Direction().XYZ(),
-             S.Location().XYZ() + VMax*S.Axis().Direction().XYZ(),B);
+             gp_Pnt(S.XAxis().Direction().XYZ()),
+             gp_Pnt(S.YAxis().Direction().XYZ()),
+             gp_Pnt(S.Location().XYZ() + VMax*S.Axis().Direction().XYZ()),B);
     }
   }
 
     }
     else {
       Compute(UMin,UMax,R+VMax*Sin(A),R+VMax*Sin(A),
-             S.XAxis().Direction().XYZ(),
-             S.YAxis().Direction().XYZ(),
-             S.Location().XYZ() + 
-             VMax*Cos(A)*S.Axis().Direction().XYZ(),B);
+             gp_Pnt(S.XAxis().Direction().XYZ()),
+             gp_Pnt(S.YAxis().Direction().XYZ()),
+             gp_Pnt(S.Location().XYZ() + 
+             VMax*Cos(A)*S.Axis().Direction().XYZ()),B);
       gp_Dir D(Cos(A)*S.Axis().Direction());
       OpenMin(D,B);     
     }
     }
     else {
       Compute(UMin,UMax,R+VMax*Sin(A),R+VMax*Sin(A),
-             S.XAxis().Direction().XYZ(),
-             S.YAxis().Direction().XYZ(),
-             S.Location().XYZ() + 
-             VMax*Cos(A)*S.Axis().Direction().XYZ(),B);
+             gp_Pnt(S.XAxis().Direction().XYZ()),
+             gp_Pnt(S.YAxis().Direction().XYZ()),
+             gp_Pnt(S.Location().XYZ() + 
+             VMax*Cos(A)*S.Axis().Direction().XYZ()),B);
       gp_Dir D(Cos(A)*S.Axis().Direction());
       OpenMax(D,B);
     }
   }
   else {
     Compute(UMin,UMax,R+VMin*Sin(A),R+VMin*Sin(A),
-           S.XAxis().Direction().XYZ(),
-           S.YAxis().Direction().XYZ(),
-           S.Location().XYZ() + 
-           VMin*Cos(A)*S.Axis().Direction().XYZ(),B);
+           gp_Pnt(S.XAxis().Direction().XYZ()),
+           gp_Pnt(S.YAxis().Direction().XYZ()),
+           gp_Pnt(S.Location().XYZ() + 
+           VMin*Cos(A)*S.Axis().Direction().XYZ()),B);
     if (Precision::IsNegativeInfinite(VMax)) {
       gp_Dir D(Cos(A)*S.Axis().Direction());
       OpenMin(D,B);
     }
     else {
       Compute(UMin,UMax,R+VMax*Sin(A),R+VMax*Sin(A),
-             S.XAxis().Direction().XYZ(),
-             S.YAxis().Direction().XYZ(),
-             S.Location().XYZ() + 
-             VMax*Cos(A)*S.Axis().Direction().XYZ(),B);
+             gp_Pnt(S.XAxis().Direction().XYZ()),
+             gp_Pnt(S.YAxis().Direction().XYZ()),
+             gp_Pnt(S.Location().XYZ() + 
+             VMax*Cos(A)*S.Axis().Direction().XYZ()),B);
     }
   }
 
  if (-Fi1>Precision::Angular()) {
    if (-Fi2>Precision::Angular()) {
      Compute(UMin,UMax,S.Radius(),S.Radius(),
-              S.XAxis().Direction().XYZ(),S.YAxis().Direction().XYZ(),
-              S.Location().XYZ(),B);
+              gp_Pnt(S.XAxis().Direction().XYZ()),gp_Pnt(S.YAxis().Direction().XYZ()),
+              S.Location(),B);
      Compute(UMin,UMax,S.Radius(),S.Radius(),
-              S.XAxis().Direction().XYZ(),S.YAxis().Direction().XYZ(),
-     S.Location().XYZ()- S.Radius()*S.Position().Axis().Direction().XYZ(),B);
+              gp_Pnt(S.XAxis().Direction().XYZ()),gp_Pnt(S.YAxis().Direction().XYZ()),
+     gp_Pnt(S.Location().XYZ()- S.Radius()*S.Position().Axis().Direction().XYZ()),B);
    }
    else {
      Compute(UMin,UMax,S.Radius(),S.Radius(),
-     S.XAxis().Direction().XYZ(),S.YAxis().Direction().XYZ(),
-     S.Location().XYZ()+ S.Radius()*S.Position().Axis().Direction().XYZ(),B);
+     gp_Pnt(S.XAxis().Direction().XYZ()),gp_Pnt(S.YAxis().Direction().XYZ()),
+     gp_Pnt(S.Location().XYZ()+ S.Radius()*S.Position().Axis().Direction().XYZ()),B);
      Compute(UMin,UMax,S.Radius(),S.Radius(),
-     S.XAxis().Direction().XYZ(),S.YAxis().Direction().XYZ(),
-     S.Location().XYZ()- S.Radius()*S.Position().Axis().Direction().XYZ(),B);
+     gp_Pnt(S.XAxis().Direction().XYZ()),gp_Pnt(S.YAxis().Direction().XYZ()),
+     gp_Pnt(S.Location().XYZ()- S.Radius()*S.Position().Axis().Direction().XYZ()),B);
    }
  }
  else {
    Compute(UMin,UMax,S.Radius(),S.Radius(),
-            S.XAxis().Direction().XYZ(),S.YAxis().Direction().XYZ(),
-            S.Location().XYZ(),B);
+            gp_Pnt(S.XAxis().Direction().XYZ()),gp_Pnt(S.YAxis().Direction().XYZ()),
+            S.Location(),B);
    Compute(UMin,UMax,S.Radius(),S.Radius(),
-   S.XAxis().Direction().XYZ(),S.YAxis().Direction().XYZ(),
-   S.Location().XYZ() +S.Radius()*S.Position().Axis().Direction().XYZ(),B);
+   gp_Pnt(S.XAxis().Direction().XYZ()),gp_Pnt(S.YAxis().Direction().XYZ()),
+   gp_Pnt(S.Location().XYZ() +S.Radius()*S.Position().Axis().Direction().XYZ()),B);
  } 
  B.Enlarge(Tol);
 #else
   if (Fi2<Fi1) return;
 
 #define SC 0.71
-#define addP0    (Compute(UMin,UMax,Ra+Ri,Ra+Ri,S.XAxis().Direction().XYZ(),S.YAxis().Direction().XYZ(),S.Location().XYZ(),B))
-#define addP1    (Compute(UMin,UMax,Ra+Ri*SC,Ra+Ri*SC,S.XAxis().Direction().XYZ(),S.YAxis().Direction().XYZ(),S.Location().XYZ()+(Ri*SC)*S.Axis().Direction().XYZ(),B))
-#define addP2    (Compute(UMin,UMax,Ra,Ra,S.XAxis().Direction().XYZ(),S.YAxis().Direction().XYZ(),S.Location().XYZ()+Ri*S.Axis().Direction().XYZ(),B))
-#define addP3    (Compute(UMin,UMax,Ra-Ri*SC,Ra-Ri*SC,S.XAxis().Direction().XYZ(),S.YAxis().Direction().XYZ(),S.Location().XYZ()+(Ri*SC)*S.Axis().Direction().XYZ(),B))
-#define addP4    (Compute(UMin,UMax,Ra-Ri,Ra-Ri,S.XAxis().Direction().XYZ(),S.YAxis().Direction().XYZ(),S.Location().XYZ(),B))
-#define addP5    (Compute(UMin,UMax,Ra-Ri*SC,Ra-Ri*SC,S.XAxis().Direction().XYZ(),S.YAxis().Direction().XYZ(),S.Location().XYZ()-(Ri*SC)*S.Axis().Direction().XYZ(),B))
-#define addP6    (Compute(UMin,UMax,Ra,Ra,S.XAxis().Direction().XYZ(),S.YAxis().Direction().XYZ(),S.Location().XYZ()-Ri*S.Axis().Direction().XYZ(),B))
-#define addP7    (Compute(UMin,UMax,Ra+Ri*SC,Ra+Ri*SC,S.XAxis().Direction().XYZ(),S.YAxis().Direction().XYZ(),S.Location().XYZ()-(Ri*SC)*S.Axis().Direction().XYZ(),B))
+#define addP0    (Compute(UMin,UMax,Ra+Ri,Ra+Ri,gp_Pnt(S.XAxis().Direction().XYZ()),gp_Pnt(S.YAxis().Direction().XYZ()),S.Location(),B))
+#define addP1    (Compute(UMin,UMax,Ra+Ri*SC,Ra+Ri*SC,gp_Pnt(S.XAxis().Direction().XYZ()),gp_Pnt(S.YAxis().Direction().XYZ()),gp_Pnt(S.Location().XYZ()+(Ri*SC)*S.Axis().Direction().XYZ()),B))
+#define addP2    (Compute(UMin,UMax,Ra,Ra,gp_Pnt(S.XAxis().Direction().XYZ()),gp_Pnt(S.YAxis().Direction().XYZ()),gp_Pnt(S.Location().XYZ()+Ri*S.Axis().Direction().XYZ()),B))
+#define addP3    (Compute(UMin,UMax,Ra-Ri*SC,Ra-Ri*SC,gp_Pnt(S.XAxis().Direction().XYZ()),gp_Pnt(S.YAxis().Direction().XYZ()),gp_Pnt(S.Location().XYZ()+(Ri*SC)*S.Axis().Direction().XYZ()),B))
+#define addP4    (Compute(UMin,UMax,Ra-Ri,Ra-Ri,gp_Pnt(S.XAxis().Direction().XYZ()),gp_Pnt(S.YAxis().Direction().XYZ()),S.Location(),B))
+#define addP5    (Compute(UMin,UMax,Ra-Ri*SC,Ra-Ri*SC,gp_Pnt(S.XAxis().Direction().XYZ()),gp_Pnt(S.YAxis().Direction().XYZ()),gp_Pnt(S.Location().XYZ()-(Ri*SC)*S.Axis().Direction().XYZ()),B))
+#define addP6    (Compute(UMin,UMax,Ra,Ra,gp_Pnt(S.XAxis().Direction().XYZ()),gp_Pnt(S.YAxis().Direction().XYZ()),gp_Pnt(S.Location().XYZ()-Ri*S.Axis().Direction().XYZ()),B))
+#define addP7    (Compute(UMin,UMax,Ra+Ri*SC,Ra+Ri*SC,gp_Pnt(S.XAxis().Direction().XYZ()),gp_Pnt(S.YAxis().Direction().XYZ()),gp_Pnt(S.Location().XYZ()-(Ri*SC)*S.Axis().Direction().XYZ()),B))
   
   switch (Fi1) {
   case 0 :