import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;
import java.util.concurrent.Callable;
import java.util.concurrent.ExecutionException;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
import java.util.concurrent.Future;

public class Euler482 {

    static class Leg {
        long x;
        long t;

        Leg(long x, long t) {
            this.x = x;
            this.t = t;
        }
    }

    private static int maxInradiusForPerimeter(long P) {
        double bound = P * Math.sqrt(3.0) / 18.0;
        int rMax = (int) Math.floor(bound + 1e-12);
        return Math.max(0, rMax);
    }

    private static int[] buildSpf(int limit) {
        int[] spf = new int[limit + 1];
        if (limit >= 1)
            spf[1] = 1;
        for (int i = 2; i <= limit; ++i) {
            if (spf[i] == 0) {
                spf[i] = i;
                if ((long) i * i <= limit) {
                    for (long j = (long) i * i; j <= limit; j += i) {
                        if (spf[(int) j] == 0)
                            spf[(int) j] = i;
                    }
                }
            }
        }
        return spf;
    }

    private static List<int[]> factorize(int n, int[] spf) {
        List<int[]> out = new ArrayList<>();
        while (n > 1) {
            int p = spf[n];
            int cnt = 0;
            while (n % p == 0) {
                n /= p;
                cnt++;
            }
            out.add(new int[] { p, cnt });
        }
        return out;
    }

    private static List<Leg> buildLegs(int r, long r2, long maxX, int[] spf) {
        List<int[]> factors = factorize(r, spf);
        long[] divisors = new long[50000];
        int numDivisors = 1;
        divisors[0] = 1;

        for (int[] f : factors) {
            int p = f[0];
            int exp = 2 * f[1];
            long pPow = 1;
            int baseSize = numDivisors;
            for (int e = 1; e <= exp; ++e) {
                pPow *= p;
                for (int i = 0; i < baseSize; ++i) {
                    divisors[numDivisors++] = divisors[i] * pPow;
                }
            }
        }

        List<Leg> legs = new ArrayList<>();
        for (int i = 0; i < numDivisors; i++) {
            long d = divisors[i];
            if (d > r)
                continue;
            long d2 = r2 / d;
            if (((d + d2) & 1) != 0)
                continue;
            long x = (d2 - d) / 2;
            if (x <= 0 || x > maxX)
                continue;
            long t = (d2 + d) / 2;
            legs.add(new Leg(x, t));
        }
        legs.sort((a, b) -> Long.compare(a.x, b.x));
        return legs;
    }

    private static long computeSumRange(long P, int rStart, int rEnd, int[] spf) {
        long pHalf = P / 2;
        long total = 0; // Using long, P=10^7 max P is 10^7, L ~ 2*10^7, total ~ sum of L over maybe 1M
                        // elements, easily fits in 64-bit

        for (int r = rStart; r <= rEnd; ++r) {
            long r2 = (long) r * r;
            List<Leg> legs = buildLegs(r, r2, pHalf, spf);
            if (legs.size() < 2)
                continue;

            int n = legs.size();
            long[] xs = new long[n];
            long[] ts = new long[n];
            for (int i = 0; i < n; i++) {
                xs[i] = legs.get(i).x;
                ts[i] = legs.get(i).t;
            }

            for (int i = 0; i < n; ++i) {
                long x = xs[i];
                long tx = ts[i];
                for (int j = i; j < n; ++j) {
                    long y = xs[j];
                    long ty = ts[j];
                    long denom = x * y - r2;
                    if (denom <= 0)
                        continue;
                    long numer = r2 * (x + y);
                    if (numer % denom != 0)
                        continue;

                    long zU = numer / denom;
                    long maxZ = pHalf - x - y;
                    if (maxZ <= 0 || zU > maxZ)
                        continue;

                    long z = zU;
                    if (z < y)
                        continue;

                    int idx = Arrays.binarySearch(xs, z);
                    if (idx < 0)
                        continue;

                    long tz = ts[idx];
                    long p = 2 * (x + y + z);
                    long L = p + tx + ty + tz;
                    total += L;
                }
            }
        }
        return total;
    }

    private static long computeSum(long P, int[] spf, int rMax) throws InterruptedException, ExecutionException {
        if (rMax <= 0)
            return 0;

        int threads = Runtime.getRuntime().availableProcessors();
        if (threads <= 0)
            threads = 1;
        if (rMax < 200 || threads == 1) {
            return computeSumRange(P, 1, rMax, spf);
        }

        int chunk = (rMax + threads - 1) / threads;
        ExecutorService executor = Executors.newFixedThreadPool(threads);
        List<Future<Long>> futures = new ArrayList<>();

        for (int t = 0; t < threads; ++t) {
            int start = t * chunk + 1;
            int end = Math.min(rMax, start + chunk - 1);
            if (start > end)
                continue;
            futures.add(executor.submit(() -> computeSumRange(P, start, end, spf)));
        }

        long total = 0;
        for (Future<Long> f : futures) {
            total += f.get();
        }
        executor.shutdown();
        return total;
    }

    public static void main(String[] args) throws Exception {
        long P = 10000000L;
        int rMax = maxInradiusForPerimeter(P);
        int[] spf = buildSpf(rMax);
        long answer = computeSum(P, spf, rMax);
        System.out.println(answer);
    }
}
