#include <bits/stdc++.h>

using namespace std;

template<typename T>
struct Point2D {
  T x, y;

  Point2D(T x = 0, T y = 0) : x(x), y(y) {}

  bool operator==(const Point2D &p) const { return x == p.x && y == p.y; }
  bool operator!=(const Point2D &p) const { return x != p.x || y != p.y; }

  Point2D  operator+ (const Point2D &p) const { return Point2D(x + p.x, y + p.y); }
  Point2D  operator- (const Point2D &p) const { return Point2D(x - p.x, y - p.y); }
  Point2D& operator+=(const Point2D &p) { x += p.x; y += p.y; return *this; }
  Point2D& operator-=(const Point2D &p) { x -= p.x; y -= p.y; return *this; }

  Point2D  operator* (T k) const { return Point2D(x * k, y * k); }
  Point2D  operator/ (T k) const { return Point2D(x / k, y / k); }
  Point2D& operator*=(T k) { x *= k; y *= k; return *this; }
  Point2D& operator/=(T k) { x /= k; y /= k; return *this; }

  T operator*(const Point2D &p) const { return x * p.x + y * p.y; }

  T dist_pow2() const { return x * x + y * y; }

  bool operator< (const Point2D &p) const {
    return dist_pow2() == p.dist_pow2() 
         ? ( y == p.y
             ? x < p.x
             : y < p.y )
         : dist_pow2() <  p.dist_pow2();
  }
  bool operator> (const Point2D &p) const {
    return dist_pow2() == p.dist_pow2()
         ? ( y == p.y
             ? x > p.x
             : y > p.y )
         : dist_pow2() >  p.dist_pow2();
  }
  bool operator<=(const Point2D &p) const { return (*this == p) || (*this < p); }
  bool operator>=(const Point2D &p) const { return (*this == p) || (*this > p); }
};

template<typename T>
std::istream& operator>>(std::istream &is, Point2D<T> &p)
{
  is >> p.x >> p.y;
  return is;
}

template<typename T>
std::ostream& operator<<(std::ostream &os, const Point2D<T> &p)
{
  os << p.x << ' ' << p.y;
  return os;
}

typedef Point2D<int64_t> Point;

namespace IntegerMath
{
  int64_t floor_div(int64_t x, int64_t y) {
    return static_cast<int64_t>(
      ::floorl(
        static_cast<long double>(x)
        /
        static_cast<long double>(y)
      )
    );
  }
  
  int64_t ceil_div(int64_t x, int64_t y) {
    return static_cast<int64_t>(
      ::ceill(
        static_cast<long double>(x)
        /
        static_cast<long double>(y)
      )
    );
  }
  
  int64_t sqrt(int64_t x) {
    return static_cast<int64_t>(
      ::floorl( ::sqrtl( 
        static_cast<long double>(x)
      ) )
    );
  }

  int64_t log2(int64_t x) {
    return static_cast<int64_t>(
      ::floorl( ::log2l( 
        static_cast<long double>(x)
      ) )
    );
  }    

  int64_t log10(int64_t x) {
    return static_cast<int64_t>(
      ::floorl( ::log10l( 
        static_cast<long double>(x)
      ) )
    );
  }

  int64_t number_of_digits(int64_t x) {
    return static_cast<int64_t>(
      ::ceill( ::log10l( 
        static_cast<long double>(x + 1)
      ) )
    );
  }

  uint64_t gcd(uint64_t a, uint64_t b)
  {
    uint64_t n = std::min(a, b), m = std::max(a, b);
    return (n == 0) ? m : gcd(m % n, n);
  }

  uint64_t lcm(uint64_t a, uint64_t b)
  {
    uint64_t d = gcd(a, b);
    return (a % d == 0) ? (a / d) * b : a * (b / d);
  }
};

vector<Point> type_a(int64_t X, int64_t Y, int64_t K, int64_t n)
{
  const array<Point, 3> Dir = {{ Point(0, -1), Point(+1, 0), Point(0, +1) }};
  vector<int64_t> D = {{ (K * n - X - Y) / 2, X, (K * n - X + Y) / 2 }};
  
  vector<Point> v;
  Point p(0, 0);
  int64_t d = 0, L = K, i = 0;
  
  while (d < 3) {
    if (D[d] < L) {
      L -= D[d];
      
      p = p + (Dir[d] * D[d]);
      D[d] = 0;
      
      ++d;
    } else { // D[d] >= L
      D[d] -= L;
      p = p + (Dir[d] * L);
      
      v.push_back(p);
      ++i;
      
      L = K;
    }
    
    if (d == 2 && D[d] <= 0) { break; }
  }
  
  if (v.size() < n) {
    v.push_back(p);
  }
  
  return v;
}

vector<Point> type_b(int64_t X, int64_t Y, int64_t K)
{
  const array<Point, 4> Dir = {{ Point(0, -1), Point(+1, 0), Point(0, +1), Point(-1, 0) }};
  vector<int64_t> D = {{ K - X, X + (K + X - Y) / 2, K - X + Y, (K + X - Y) / 2 }};
  
  vector<Point> v;
  Point p(0, 0);
  int64_t d = 0, L = K, i = 0;
  
  while (d < 4) {
    if (D[d] < L) {
      L -= D[d];
      
      p += Dir[d] * D[d];
      D[d] = 0;
      
      ++d;
    } else { // D[d] >= L
      D[d] -= L;
      p += Dir[d] * L;
      
      v.push_back(p);
      ++i;
      
      L = K;
    }
    
    if (d == 3 && D[d] <= 0) { break; }
  }
  
  if (v.size() < 3) {
    v.push_back(p);
  }
  
  return v;
}

int main()
{
  int64_t K;
  cin >> K;
  
  int64_t X, Y;
  cin >> X >> Y;
  
  bool x_sign = false, y_sign = false, xy_swap = false;
  if (X < 0) { X *= -1; x_sign = true; }
  if (Y < 0) { Y *= -1; y_sign = true; }
  if (X < Y) { swap(X, Y); xy_swap = true; }
  
  int64_t Z = X + Y;
  
  if ((K % 2 == 0) && (Z % 2 == 1)) {
    cout << -1 << endl;
    return 0;
  }
  
  int64_t n = -1;
  if (Z < K) {
    n = 2 + (Z % 2);
  } else {
    int64_t c = (K - (Z % K)) % K;
    n = IntegerMath::ceil_div(Z, K) + (c % 2);
  }
  
  vector<Point> ans;
  if ((Z < K) && (Z % 2 == 1)) {
    ans = type_b(X, Y, K);
  } else {
    ans = type_a(X, Y, K, n);
  }
  
  cout << ans.size() << endl;
  for (Point &p : ans) {
    if (xy_swap) { swap(p.x, p.y); }
    if (x_sign) { p.x *= -1; }
    if (y_sign) { p.y *= -1; }
    cout << p << endl;
  }
  
  return 0;
}

Measured memory_bytes: 6128