#include <bits/stdc++.h>
#define TASK "mountain"
#define sz(x) ((int)((x).size()))

using namespace std;

typedef long long ll;
typedef pair < ll , ll > lpair;
const int DX[] = {1, 0,-1, 0};
const int DY[] = {0, 1, 0,-1};
const int EPS = 1e-8;
const double DINF = numeric_limits<double>::infinity();

const int C = 1000000001;
const int N = 1 << 19;

struct Vec2
{
	double x, y;
	bool operator < (const Vec2 & b) const
	{
		return x < b.x;
	}
};

struct Line
{
	ll k, b;
	double operator () (double x) const
	{
		return k*x + b;
	}
	ll operator () (ll x) const
	{
		return k*x + b;
	}
	ll operator () (int x) const
	{
		return k*x + b;
	}
};

Vec2 intersect(const Line & q, const Line & w)
{
	double x = 1.*(w.b-q.b)/(q.k-w.k);
	return {x, q(x)};
}

int n, q;
ll mx, px[N], py[N];
Line lom[N];

struct HPI
{
	vector < Line > lines; 
	vector < Vec2 > points;

	void add(const Line & nl)
	{
		if (lines.empty())
		{
			lines.push_back(nl);
			points.push_back({0, nl(0)});
			points.push_back({mx, nl(mx)});
			return;
		}
		if (points.back().y >= nl(mx))
			return;
		if (points[0].y <= nl(0))
		{
			points.clear();
			lines.clear();
			lines.push_back(nl);
			points.push_back({0, nl(0)});
			points.push_back({mx, nl(mx)});
			return;
		}
		Line prevl;
		while (true)
		{
			Vec2 p = points.back();
			if (p.y <= nl(p.x))
			{
				points.pop_back();
				prevl = lines.back();
				lines.pop_back();
			}
			else
			{
				points.push_back(intersect(prevl, nl));
				points.push_back({mx, nl(mx)});
				lines.push_back(prevl);
				lines.push_back(nl);
				return;
			}
		}
	}

	bool inside(ll tx, ll ty) const
	{
		if (lines.empty())
			return true;
		int cseg = min(sz(lines) - 1, int(upper_bound(points.begin(), points.end(), Vec2({tx, DINF})) - points.begin() - 1));
		return ty >= lines[cseg](tx);
	}
};

HPI merge(const HPI & a, const HPI & b)
{
	HPI c;
	int p1 = 0, p2 = 0;
	while (true)
	{
		if (p1 == sz(a.lines))
		{
			if (p2 == sz(b.lines))
				return c;
			c.add(b.lines[p2++]);
		} else if (p2 == sz(b.lines) || a.lines[p1].k < b.lines[p2].k)
			c.add(a.lines[p1++]);
		else
			c.add(b.lines[p2++]);
	}
}

class SegTree
{
	HPI t[N*2-1];
	int n;
public:
	void init(int nn, Line * l)
	{
		n = nn;
		for (int i = 0; i < n; ++i)
			t[i+N-1].add(l[i]);
		for (int i = N - 2; i >= 0; --i)
			t[i] = merge(t[i*2+1], t[i*2+2]);
	}

	int solveL(int start, ll tx, ll ty, int c = 0, int cl = 0, int cr = N - 1)
	{
		if (cl > start)
			return -1;
		int c1 = c*2 + 1;
		int c2 = c*2 + 2;
		int mid = (cl + cr) / 2;
		if (cr > start)
		{
			int ans = solveL(start, tx, ty, c2, mid+1, cr);
			if (ans == -1)
				return solveL(start, tx, ty, c1, cl, mid);
			return ans;
		}
		if (t[c].inside(tx, ty))
			return -1;
		if (cl == cr)
			return cl;
		int ans = solveL(start, tx, ty, c2, mid+1, cr);
		if (ans == -1)
			return solveL(start, tx, ty, c1, cl, mid);
		return ans;
	}
	int solveR(int start, ll tx, ll ty, int c = 0, int cl = 0, int cr = N - 1)
	{
		if (cr < start)
			return n;
		int c1 = c*2 + 1;
		int c2 = c*2 + 2;
		int mid = (cl + cr) / 2;
		if (cl < start)
		{
			int ans = solveR(start, tx, ty, c1, cl, mid);
			if (ans == n)
				return solveR(start, tx, ty, c2, mid + 1, cr);
			return ans;
		}
		if (t[c].inside(tx, ty))
			return n;
		if (cl == cr)
			return cl;
		int ans = solveR(start, tx, ty, c1, cl, mid);
		if (ans == n)
			return solveR(start, tx, ty, c2, mid + 1, cr);
		return ans;
	}
} st;


int main()
{
#ifndef LOCAL
	freopen(TASK".in", "r", stdin);
	freopen(TASK".out", "w", stdout);
#endif
	ios::sync_with_stdio(false);

	cin >> n >> q;
	for (int i = 1; i <= n; ++i)
	{
		int d, k;
		cin >> d >> k;
		px[i] = px[i - 1] + d;
		py[i] = py[i - 1] + 1LL*d*k;
		lom[i - 1] = {k, py[i-1] - px[i-1]*k};
		mx += d;
	}
	st.init(n, lom);

	for (int i = 0; i < q; ++i)
	{
		ll tx, ty;
		cin >> tx >> ty;
		int cseg = min(n - 1, int(upper_bound(px, px + n + 1, tx) - px - 1));
		int ansL = st.solveL(cseg, tx, ty);
		int ansR = st.solveR(cseg, tx, ty);
		cout << px[ansL + 1] << " " << px[ansR] << "\n";
	}

	return 0;
}
