#include <bits/stdc++.h>
using namespace std;
inline int nextInt() {
  int res;
  assert(cin >> res);
  return res;
}
const int N = (int)1e5;
bool isPrime[N + 1];
bool used[N + 1];
int main() {
  ios::sync_with_stdio(false);
  int n = nextInt();
  vector<pair<int, int> > res;
  for (int i = 2; i <= n; ++i) isPrime[i] = true;
  for (int i = 2; i * i <= n; ++i)
    if (isPrime[i])
      for (int j = i * i; j <= n; j += i)
        if (isPrime[j]) isPrime[j] = false;
  for (int p = 3; 2 * p <= n; ++p)
    if (isPrime[p]) {
      int cnt = 0;
      for (int x = p; x <= n; x += p)
        if (!used[x]) ++cnt;
      if (cnt % 2 == 1) used[2 * p] = true;
      for (int x = p, last = -1; x <= n; x += p)
        if (!used[x]) {
          if (last != -1) {
            res.push_back(make_pair(last, x));
            used[last] = used[x] = true;
            last = -1;
          } else {
            last = x;
          }
        }
      if (cnt % 2 == 1) used[2 * p] = false;
    }
  for (int x = 2, last = -1; x <= n; x += 2)
    if (!used[x]) {
      if (last != -1) {
        res.push_back(make_pair(last, x));
        used[last] = used[x] = true;
        last = -1;
      } else {
        last = x;
      }
    }
  printf("%d\n", (int)res.size());
  for (int i = 0; i < (int)res.size(); ++i)
    printf("%d %d\n", res[i].first, res[i].second);
  return 0;
}
