#include<bits/stdc++.h>
using namespace std;
// #include"Template.cpp"


class LCP
{
public:
    string s;
    vector<int> suffix;
    vector<int> lcp;
    vector<vector<int>> table;
    LCP() {}
    LCP(string st)
    {
        s = st;
    }
    void CountSort(vector<int> &p, vector<int> &c)
    {
        int n = p.size();
        vector<int> cnt(n);
        for (auto x : c)
        {
            cnt[x]++;
        }
        vector<int> newp(n);
        vector<int> pos(n);
        pos[0] = 0;
        for (int i = 1; i < n; i++)
        {
            pos[i] = pos[i - 1] + cnt[i - 1];
        }
        for (auto x : p)
        {
            int i = c[x];
            newp[pos[i]] = x;
            pos[i]++;
        }
        p = newp;
    }
    void buildSuffix()
    {
        s += "$";
        int n = s.size();
        suffix.assign(n, 0);
        vector<int> c(n, 0);
        vector<pair<int, int>> arr(n);
        for (int i = 0; i < n; i++)
            arr[i] = {s[i], i};
        sort(arr.begin(), arr.end());
        for (int i = 0; i < n; i++)
            suffix[i] = arr[i].second;
        c[suffix[0]] = 0;
        for (int i = 1; i < n; i++)
        {
            if (arr[i].first == arr[i - 1].first)
            {
                c[suffix[i]] = c[suffix[i - 1]];
            }
            else
            {
                c[suffix[i]] = c[suffix[i - 1]] + 1;
            }
        }
        int k = 0;
        while ((1 << k) < n)
        {
            for (int i = 0; i < n; i++)
            {
                suffix[i] = ((suffix[i] - (1 << k)) + n) % n;
            }
            CountSort(suffix, c);
            vector<int> newc(n, 0);
            for (int i = 1; i < n; i++)
            {
                pair<int, int> p1 = {c[suffix[i]], c[(suffix[i] + (1 << k)) % n]};
                pair<int, int> p2 = {c[suffix[i - 1]], c[(suffix[i - 1] + (1 << k)) % n]};
                if ((p1.first == p2.first) && (p1.second == p2.second))
                {
                    newc[suffix[i]] = newc[suffix[i - 1]];
                }
                else
                {
                    newc[suffix[i]] = newc[suffix[i - 1]] + 1;
                }
            }
            c = newc;
            k++;
        }
    }
    void buildLCP()
    {
        buildSuffix();
        int n = s.size(), k = 0;
        lcp.assign(n, 0);
        vector<int> rank(n, 0);
        for (int i = 0; i < n; i++)
            rank[suffix[i]] = i;

        for (int i = 0; i < n; i++, k ? k-- : 0)
        {
            if (rank[i] == n - 1)
            {
                k = 0;
                continue;
            }
            int j = suffix[rank[i] + 1];
            while (i + k < n && j + k < n && s[i + k] == s[j + k])
                k++;
            lcp[rank[i]] = k;
        }
    }
    void buildRMQ() {
        int n = lcp.size();
        int size = 30;
        table.assign(n+10, vector<int>(size, 0));
        for (int i = 0; i < n; i++)
        {
            table[i][0] = lcp[i];
        }
        for (int j = 1; j <= size; j++)
        {
            for (int i = 0; (i + (1 << j)) <= n; i++)
            {
                table[i][j] = min(table[i][j - 1], table[i + (1 << (j - 1))][j - 1]);
            }
        }
    }
    int query(int l, int r) {
        if(l > r) swap(l, r);
        int index = (int)(log2(r - l + 1));
        return min(table[l][index], table[r - (1 << index) + 1][index]);
    }
};

vector<vector<int>> divisor;
vector<int> Index;
LCP lcp;

bool isGood(int l, int r) {
    int len = r - l + 1;
    for(auto div : divisor[len]) {
        int st = min(Index[l], Index[l+div]);
        int en = max(Index[l], Index[l + div]) - 1;
        int minn = lcp.query(st, en);
        if(minn >= (len - div)) {
            return 0;
        }
    }
    return 1;
}

void solve(string s, int n)
{
    lcp.s = s;
    lcp.buildLCP();
    lcp.buildRMQ();
    divisor.resize(n+1);
    for (auto i = 1; i <= n; ++i)
    {
        for (auto j = 2; i * j <= n; ++j)
        {
            divisor[i * j].push_back(i);
        }
    }
    Index.assign(n+1, 0);
    bool pos = 1;
    for(int i = 0; i < (int)lcp.suffix.size(); i ++) Index[lcp.suffix[i]] = i; 
    for(int i = 0; i < n; i ++) {
        if(s[i] != s[0]) {
            pos = 0;
            break;
        }
    }
    if(pos) {
        cout << n << endl << 1 << endl;
        return ;
    }
    if(isGood(0, n-1)) {
        cout << 1 << endl << 1 << endl;
        return ; 
    }
    int ans = 0;
    for(int i = 0; i < n-1; i ++) {
        if(isGood(0, i) && isGood(i+1, n-1)) {
            ans ++;
        }
    }
    cout << 2 << endl << ans << endl;
}  

int32_t main()
{
    ios_base::sync_with_stdio(0);
    cin.tie(0);
    cout.tie(0);
    string s;
    int n;
    cin >> s;
    n = s.size();
    solve(s, n);
    return 0;
}

Measured memory_bytes: 140372