import java.io.*;
import java.util.ArrayList;
import java.util.Collections;
import java.util.TreeSet;

public class tesseract_ak_hash {

    static class Segment implements Comparable<Segment> {
        int left, right;
        static int ID = 0;
        int id;

        Segment(int left, int right) {
            this.left = left;
            this.right = right;
            id = ID++;
        }

        boolean inside(Segment s) {
            if (left == s.left && right == s.right)
                return false;
            if (s.left <= left && right <= s.right)
                return true;
            return false;
        }

        @Override
        public int compareTo(Segment s) {
            if (left != s.left)
                return left - s.left;
            if (right == s.right && id != s.id) {
                throw new AssertionError("Arrrr! Equal segments");
            }
            return s.right - right;
        }

        @Override
        public String toString() {
            return "[" + left + "; " + right + ")";
        }
    }

    static class Event implements Comparable<Event> {
        static int ID = 0;
        int id;
        int pos;
        Segment s;
        Type type;

        Event(int pos, Segment s, Type type) {
            this.pos = pos;
            this.s = s;
            this.type = type;
            id = ID++;
        }

        @Override
        public int compareTo(Event e) {
            if (e.pos != pos) {
                return pos - e.pos;
            }
            if (e.type != type) {
                return type.compareTo(e.type);
            }
            int sign = s.compareTo(e.s);
            if (sign != 0)
                return sign * (e.type == Type.CLOSE ? -1 : 1);
            return id - e.id;
        }

        enum Type {
            OPEN, CLOSE;
        }

        @Override
        public String toString() {
            return "Event{" +
                    "pos=" + pos +
                    ", s=" + s +
                    ", type=" + type +
                    '}';
        }
    }

    static String intercalate(char sep, String s) {
        StringBuilder sb = new StringBuilder();
        int n = s.length();
        for (int i = 0; i < n - 1; i++) {
            sb.append(s.charAt(i));
            sb.append(sep);
        }
        sb.append(s.charAt(n - 1));
        return sb.toString();
    }

    static class UniHash {
        final long X;
        String s;
        long[] hash;
        long[] XPOW;
        int n;

        UniHash(long X, String s) {
            this.X = X;
            this.s = s;
            n = s.length();
            XPOW = new long[n + 1];
            XPOW[0] = 1;
            for (int i = 0; i < n; i++) {
                XPOW[i + 1] = XPOW[i] * X;
            }
            hash = new long[n + 1];
            hash[0] = 0;
            for (int i = 0; i < n; i++) {
                hash[i + 1] = hash[i] * X + s.charAt(i);
            }
        }

        long hash(int left, int right) {
            return hash[right] - hash[left] * XPOW[right - left];
        }
    }

    static class BiHash {
        static long X = 997;
        UniHash straight;
        UniHash reversed;
        int n;

        BiHash(String s) {
            String srev = new StringBuilder(s).reverse().toString();
            straight = new UniHash(X, s);
            reversed = new UniHash(X, srev);
            n = s.length();
        }

        long hash(int left, int right) {
            return straight.hash(left, right);
        }

        long rhash(int left, int right) {
            return reversed.hash(n - right, n - left);
        }

    }

    static int[] oddtesseractdromes(String s) {
        int n = s.length();
        int[] res = new int[s.length()];
        BiHash hash = new BiHash(s);
        for (int i = 0; i < n; i++) {
            int left = 1;
            int right = Math.min(i + 2, n - i + 1);
            while (left + 1 < right) {
                int mid = (left + right) / 2;
                if (hash.hash(i, i + mid) == hash.rhash(i - mid + 1, i + 1)) {
                    left = mid;
                } else {
                    right = mid;
                }
            }
            res[i] = left;
        }
        return res;
    }

    static long solve(String s) {
        int n = s.length();
//        System.err.println(s);
        String s2 = intercalate('$', s);
        int[] a = oddtesseractdromes(s2);
//        System.err.println(s2);
//        System.err.println(Arrays.toString(a));
        ArrayList<Segment> segments = new ArrayList<>();
        for (int i = 0; i < n; i++) {
            segments.add(new Segment(i - (a[2 * i] - 1) / 2, i + (a[2 * i] - 1) / 2 + 1));
            if (i != n - 1 && a[2 * i + 1] > 1) {
                segments.add(new Segment(i - a[2 * i + 1] / 2 + 1, i + a[2 * i + 1] / 2 + 1));
            }
        }
//        System.err.println(segments);
//        for (Segment ss : segments) {
//            System.err.println(ss + " " + s.substring(ss.left, ss.right));
//        }
        long ans = 0;
        for (Segment ss : segments) {
            if (ss.right - ss.left > 2) {
                ans += (ss.right - ss.left - 1) / 2;
            }
        }
//        System.err.println(ans);
        ArrayList<Event> events = new ArrayList<>();
        for (Segment ss : segments) {
            events.add(new Event(ss.left, ss, Event.Type.OPEN));
            events.add(new Event(ss.right, ss, Event.Type.CLOSE));
        }
        Collections.sort(events);
//        System.err.println(events);
        TreeSet<Segment> set = new TreeSet<>();
        for (Event e : events) {
            if (e.type == Event.Type.OPEN) {
                set.add(e.s);
            } else {
                set.remove(e.s);
                if (set.isEmpty())
                    continue;
                Segment fst = set.first();
                if (e.s.inside(fst)) {
                    ans++;
//                    System.err.println(e.s + " is good");
                }
            }
        }
        System.err.println(ans);
        return ans;
    }

    public static void main(String[] args) throws IOException {
        BufferedReader br = new BufferedReader(new FileReader(new File("tesseract.in")));
        PrintWriter out = new PrintWriter("tesseract.out");
        long ans = solve(br.readLine());
        out.println(ans);
        out.close();
    }
}
