#define _CRT_SECURE_NO_WARNINGS

#include <vector>
#include <iostream>
#include <string>
#include <functional>
#include <set>
#include <map>
#include <unordered_map>
#include <fstream>
#include <iomanip>
#include <ctime>
#include <queue>
#include <deque>
#include <math.h>
#include <cmath>
#include <stack>
#include <algorithm>
#include <list>
#include <array>
#include <valarray>
#include <unordered_map>
#include <cassert>
#include <random>
#include <cstring>
#include <sstream>
#include <numeric>
#include <iterator>

using namespace std;

#define x first
#define y second
#define mp make_pair
#define pb push_back
#define sqr(a) ((a) * (a))
#define sz(a) int((a).size())
#define all(a) a.begin(), a.end()
#define forn(i, n) for(int i = 0; i < int(n); i++) 
#define fore(i, l, r) for(int i = int(l); i < int(r); i++)
#define vec vector

typedef long long li;
typedef long long ll;
typedef long double ld;
typedef pair<int, int> pt;
typedef pair<int, int> pii;

template <class A, class B> ostream& operator << (ostream& out, const pair<A, B>& a) {
	return out << "(" << a.x << ", " << a.y << ")";
}

template <class A> ostream& operator << (ostream& out, const vector<A>& v) {
	out << "[";
	forn(i, sz(v)) {
		if (i) out << ", ";
		out << v[i];
	}
	return out << "]";
}

mt19937 rnd(time(NULL));

const int INF = int(1e9);
const li INF64 = li(1e18);
const int MOD = INF + 7;
const ld EPS = 1e-9;
const ld PI = acos(-1.0);
//const li MOD = 100055128505716009;
//const li P = 3e4 + 11;

const int N = 1e5 + 7;

vector<int> g[N];
int n;
set<pt> have;

vector<int> get(int x, int y) {
	//cout << x << ' ' << y << endl;
	vector<int> res;
	for (int v : g[x]) {
		if (binary_search(all(g[y]), v)) {
			//cout << "FOUND " << v << endl;
			res.pb(v);
		}
	}

	return res;
}

vector<int> tryLR() {
	for (int r : g[0]) {
		vector<int> ans;

		int l = 0;
		ans.push_back(l);

		auto it = get(l, r);
		if (sz(it) != 1) {
			continue;
		}

		//cout << l << ' ' << r << ' ' << it << endl;
		int m = it[0];
		ans.push_back(m);
		ans.push_back(r);

		while (1) {
			auto it = get(m, r);

			if (sz(it) != 2) {
				return {};
			}

			int v = it[0];
			if (v == l) {
				v = it[1];
			}

			if (v == 0) {
				return ans;
			}

			ans.pb(v);

			l = m;
			m = r;
			r = v;
		}
	}
}

bool check(vector<int>& ans) {
	if (sz(ans) != n) {
		return false;
	}

	bool res = true;
	forn(i, n) {
		int x = ans[i];
		int y = ans[(i + 1) % n];
		if (x > y) {
			swap(x, y);
		}

		res &= bool(have.count({ x, y }));

		x = ans[i];
		y = ans[(i + 2) % n];
		if (x > y) {
			swap(x, y);
		}

		res &= bool(have.count({ x, y }));
	}

	return res;
}

int main() {
#ifdef _DEBUG
	freopen("input.txt", "r", stdin);
	freopen("output.txt", "w", stdout);

	int tt = clock();
#endif

	ios::sync_with_stdio(0);
	cin.tie(0);

	cerr.precision(15);
	cout.precision(15);
	cerr << fixed;
	cout << fixed;

	// SOLUTION GOES HERE

	int n, w;
	cin >> n >> w;
	
	vector<pt> a(n);
	vector<vector<int>> vals(4);
	forn(i, n) {
		cin >> a[i].x >> a[i].y;
		vals[a[i].x - a[0].x].pb(a[i].y);
	}

	vector<vector<li>> sums(4);
	forn(i, 4) {
		sort(all(vals[i]));
		reverse(all(vals[i]));

		sums[i] = { 0 };
		forn(j, sz(vals[i])) {
			sums[i].pb(sums[i].back() + vals[i][j]);
		}
	}

	li ans = 0;
	forn(cnt1, sz(sums[0])) {
		forn(cnt2, sz(sums[1])) {
			forn(cnt3, sz(sums[2])) {
				forn(cnt4, sz(sums[3])) {
					if ((cnt2 + cnt3 * 2 + cnt4 * 3) + (cnt1 + cnt2 + cnt3 + cnt4) * 1ll * a[0].x > w) {
						continue;
					}
					ans = max(ans, sums[0][cnt1] + sums[1][cnt2] + sums[2][cnt3] + sums[3][cnt4]);
				}
			}
		}
	}

	cout << ans << endl;

	// SOLUTION ENDS HERE


#ifdef _DEBUG 
	cout << "TIME = " << clock() - tt << endl;
	tt = clock();
#endif
}

Measured memory_bytes: 2560