Lavrenty, a baker, is going to make several buns with stuffings and sell them.Lavrenty has n grams of dough as well as m different stuffing types. The stuffing types are numerated from 1 to m. Lavrenty knows that he has ai grams left of the i-th stuffing. It takes exactly bi grams of stuffing i and ci grams of dough to cook a bun with the i-th stuffing. Such bun can be sold for di tugriks.Also he can make buns without stuffings. Each of such buns requires c0 grams of dough and it can be sold for d0 tugriks. So Lavrenty can cook any number of buns with different stuffings or without it unless he runs out of dough and the stuffings. Lavrenty throws away all excess material left after baking.Find the maximum number of tugriks Lavrenty can earn.

The first line contains 4 integers n, m, c0 and d0 (1 ≤ n ≤ 1000, 1 ≤ m ≤ 10, 1 ≤ c0, d0 ≤ 100). Each of the following m lines contains 4 integers. The i-th line contains numbers ai, bi, ci and di (1 ≤ ai, bi, ci, di ≤ 100).

Print the only number — the maximum number of tugriks Lavrenty can earn.

NoteTo get the maximum number of tugriks in the first sample, you need to cook 2 buns with stuffing 1, 4 buns with stuffing 2 and a bun without any stuffing.In the second sample Lavrenty should cook 4 buns without stuffings.

N,M,A,B = map(int,raw_input().split())
dp = [0 for x in range(N+1)]
for i in range(M):
    a,b,c,d = map(int,raw_input().split())
    for j in range(N-1,-1,-1):
        for k in range(1,a/b+1):
            if k*c+j>N:
                continue
            dp[k*c+j] = max(dp[k*c+j],dp[j]+d*k)
ans = 0
for i in range(N+1):
    ans = max(ans,dp[i]+(N-i)/A*B)
print ans

import sys
input = sys.stdin.readline

n, m, c_0, d_0 = map(int, input().split())

 # dp[grams_of_dough][1..j stuffings]
dp = [[0 for _ in range(m + 1)] for _ in range(n + 1)]

# grams left, grams required, dough required, sell price
stuffing = [(0, 1, 0, 0)] + [map(int, input().split()) for _ in range(m)]

for i in range(0, n + 1):
  for j in range(1, m + 1):
    # attempt to make k of j-stuffed thingies
    for k in range(stuffing[j][0] / stuffing[j][1] + 1):
      if i - stuffing[j][2] * k > -1:
        dp[i][j] = max(dp[i - stuffing[j][2] * k][j - 1] + stuffing[j][3] * k, dp[i][j])

ans = 0
# for row in dp: print row
for k in range(n + 1):
  ans = max(ans, dp[k][m] + ((n - k) / c_0) * d_0)

print ans

from sys import stdin, setrecursionlimit
from collections import *
import threading

def arr_inp(n):
    if n == 1:
        return [int(x) for x in stdin.readline().split()]
    elif n == 2:
        return [float(x) for x in stdin.readline().split()]
    else:
        return list(stdin.readline()[:-1])

def dp(i, rem):
    if rem == 0:
        return 0
    if i >= len(arr):
        if rem:
            return d0 * (rem // c0)
        else:
            return 0

    if mem[i][rem] != -1:
        return mem[i][rem]

    ans1, ans2, ans3 = dp(i + 1, rem), 0, 0

    if rem - arr[i][0] >= 0:
        ans2 = arr[i][1] + dp(i + 1, rem - arr[i][0])
    if rem - c0 >= 0:
        ans3 = d0 + dp(i + 1, rem - c0)

    mem[i][rem] = max(ans1, ans2, ans3)
    return mem[i][rem]

def main():
    print(dp(0, n))

if __name__ == '__main__':
    n, m, c0, d0 = arr_inp(1)
    staff, arr, mem = [arr_inp(1) for i in range(m)], [], [[-1 for i in range(1001)] for j in range(1001)]

    for a in staff:
        arr.extend([[a[2], a[3]] for i in range(a[0] // a[1])])

    setrecursionlimit(2000)
    threading.stack_size(102400000)
    thread = threading.Thread(target=main)
    thread.start()

import sys

sys.setrecursionlimit(10 ** 6)

def pyes_no(condition) :
  if condition :
    print ("YES")
  else :
    print ("NO")

def plist(a, s = ' ') :
  print (s.join(map(str, a)))

def rint() :
  return int(sys.stdin.readline())

def rints() :
  return map(int, sys.stdin.readline().split())

def rfield(n, m = None) :
  if m == None :
    m = n

  field = []
  for i in xrange(n) :
    chars = sys.stdin.readline().strip()
    assert(len(chars) == m)
    field.append(chars)
  return field

def pfield(field, separator = '') :
  print ('\n'.join(map(lambda x: separator.join(x), field)))

def check_field_equal(field, i, j, value) :
  if i >= 0 and i < len(field) and j >= 0 and j < len(field[i]) :
    return value == field[i][j]
  return None

def digits(x, p) :
  digits = []
  while x > 0 :
    digits.append(x % p)
    x //= p
  return digits

def modpower(a, n, mod) :
  r = a ** (n % 2)
  if n > 1 :
    r *= modpower(a, n // 2, mod) ** 2
  return r % mod

def gcd(a, b) :
  if a > b :
    a, b = b, a

  while a > 0 :
    a, b = b % a, a

  return b

n, m, c0, d0 = rints()
n += 1

prev = [0] * n
for i in range((n - 1) / c0 + 1) :
  prev[i * c0] = i * d0

for i in range(m) :
  new = prev[:]
  a, b, c, d = rints()
  for start in range(n) :
    for bake in range(1, min((n - start - 1) / c + 1, a / b + 1)) :
      new[start + bake * c] = max(new[start + bake * c], prev[start] + bake * d, prev[start + bake * c])

  prev = new

print max(prev)

n = [int(i) for i in raw_input().split()]
ab = [[0,0] for i in xrange(n[1])]
cd = [[0,0] for i in xrange(n[1])]
for i in xrange(n[1]):
	x = [int(j) for j in raw_input().split()]
	ab[i][0] = x[0];ab[i][1] = x[1];cd[i][0] = x[2];cd[i][1] = x[3]
dp = [[0 for i in xrange(n[1])] for j in xrange(n[0] + 1)]
for i in xrange(1,n[0] + 1):
	for j in xrange(0,n[1]):
		sum1 = 0
		for k in xrange(0,ab[j][0]//ab[j][1] + 1):
			if(  i >= k * cd[j][0]):
				ol = 0
				if(j>=1):
					ol = dp[i - k*cd[j][0]][j - 1]
				sum1 = max(sum1,k*cd[j][1] +  ol)
		sum2 = 0
		if(j>=1):
			sum2 = dp[i][j - 1]
		#print(sum1,sum2)
		dp[i][j] = max(sum1,sum2)
maximum = 0
for i in xrange(n[0] + 1):
	maximum = max(maximum,dp[i][n[1] - 1] + (n[0] - i)//n[2] * n[3])
print(maximum)

n, m, c0, d0 = list(map(int, input().split()))

A, B, C, D = [0], [0],[0],[0]
for _ in range(m):
	a, b, c, d = list(map(int, input().split()))
	A.append(a); B.append(b); C.append(c), D.append(d);

# max money from i gram and using 1...j items.
dp = [[0]*(m+1) for _ in range(n+1)]

for i in range(n+1):
	dp[i][0] = (i//c0)*d0

for i in range(1, n+1):
	for j in range(1, m+1):

		for k in range(A[j]//B[j] + 1):
			if (i - k*C[j] >= 0):
				dp[i][j] = max( dp[i - k*C[j] ] [j-1] + k*D[j],  dp[i][j])

		dp[i][j] = max(dp[i][j], dp[i][j-1])

print(dp[n][m])

import sys
from sys import stdin, stdout
def R():
    return map(int, stdin.readline().strip().split())

n, m, c, d = R()

arr1 = []
for i in range(n//c):
    arr1.append((c, d))
for i in range(m):
    a, b, c, d = R()
    for j in range(min(a//b, n//c)):
        arr1.append((c, d))

dp = [[0 for i in range(n+1)] for i in range(len(arr1))]
if len(dp) == 0:
    print(0)
    exit()
for i in range(len(arr1)):
    c, d = arr1[i-1]
    for w in range(n+1):
        dp[i][w] = dp[i-1][w]
        if w >= c:
            if dp[i-1][w-c] + d > dp[i][w]:
                dp[i][w] = dp[i-1][w-c] + d
# print(dp, arr1)
stdout.write(str(dp[-1][-1]))
# print(arr1)
# for i in dp:
#     print(i)

# 106C

def do():
    n, m, c0, d0 = map(int, input().split(" "))
    dp = [0] * (n + 1)
    for i in range(c0, n + 1):
        dp[i] = i // c0 * d0
    for _ in range(m):
        a, b, c, d = map(int, input().split(" "))
        for i in range(n, c - 1, -1):
            for j in range(1, a // b + 1):
                if i >= j * c:
                    dp[i] = max(dp[i], dp[i - j * c] + j * d)
    return dp[-1]

print(do())

n,m,c0,d0=map(int,input().split(" "))
a,b,c,d=[0],[0],[0],[0]

for i in range(m):
    x,y,z,e=map(int,input().split(" "))
    a.append(x)
    b.append(y)
    c.append(z)
    d.append(e)

dp=[[0 for i in range(m+1)] for j in range(n+1)]

for i in range(n+1):
    for j in range(1,m+1):
        mx=0
        for k in range(a[j]//b[j]+1):
            if i>=c[j]*k:
                mx=max(dp[i-c[j]*k][j-1] + d[j]*k,mx)
        dp[i][j]=mx
ans=0

for i in range(n+1):
    ans=max(ans,dp[i][m]+((n-i)//c0)*d0)

print(ans)

# n grams of dough
# m stuffings
# a[i] grams left of stuffing i
# b[i] grams needed
# c[i] grams of dough
# d[i] price
#
# without stuffing: (special case)
# a0 = infinite
# b0 = 0
# c0 grams of dough
# d0 price
# maximize price over all buns

# at each step a choice of 1..k of m-th stuffings or no stuffing
#
# IH: we know how to find the max profit for dough n-1 and stuffings S[]
#
def f(n, a, b, c, d):
    m = len(a)
    P = [[-1] * m for _ in range(n + 1)] # n * m

    def rec(weight, index):
        if index < 0: return 0

        # memoization
        if P[weight][index] != -1:
            return P[weight][index]

        profit = 0

        # we can create at most a[i] // b[i] stuffings
        stuffing, count = 0, 0
        while stuffing <= a[index]:
            remains = weight - (count * c[index])

            # not enough dough
            if remains < 0:
                break

            prev_profit = rec(remains, index - 1)

            profit = max(profit, prev_profit + count * d[index])

            # try more stuffing
            stuffing += b[index]
            count += 1

        P[weight][index] = profit

        return profit

    ans = rec(n, m - 1)
    return ans

inf = float("inf")
A = [inf, 7,  12 ]
B = [1,   3,   3 ]
C = [2,   2,   1 ]
D = [1,  100, 10 ]
assert f(10, A, B, C, D) == 241

n, m, c0, d0 = map(int, input().split())
a, b, c, d = [inf], [0], [c0], [d0]
for _ in range(m):
    _a, _b, _c, _d = map(int, input().split())
    a.append(_a)
    b.append(_b)
    c.append(_c)
    d.append(_d)

ans = f(n, a, b, c, d)
print(ans)

from sys import stdin, setrecursionlimit

def arr_inp(n):
    if n == 1:
        return [int(x) for x in stdin.readline().split()]
    elif n == 2:
        return [float(x) for x in stdin.readline().split()]
    else:
        return list(stdin.readline()[:-1])

def dp(i, rem):
    if rem == 0:
        return 0
    if i >= len(arr):
        if rem:
            return d0 * (rem // c0)
        else:
            return 0

    if mem[i][rem] != -1:
        return mem[i][rem]

    ans1, ans2, ans3 = dp(i + 1, rem), 0, 0

    if rem - arr[i][0] >= 0:
        ans2 = arr[i][1] + dp(i + 1, rem - arr[i][0])
    if rem - c0 >= 0:
        ans3 = d0 + dp(i + 1, rem - c0)

    mem[i][rem] = max(ans1, ans2, ans3)
    return mem[i][rem]

def main():
    ans = 0
    for j in range(len(arr)):
        mem[j][n] = 0

    if arr:
        if n - arr[0][0] >= 0:
            mem[0][n - arr[0][0]] = arr[0][1]

        for j in range(1, len(arr)):
            for i in range(n + 1):
                mem[j][i] = mem[j - 1][i]

                if i + arr[j][0] <= n:
                    if mem[j - 1][i + arr[j][0]] != -1:
                        mem[j][i] = max(mem[j][i], mem[j - 1][i + arr[j][0]] + arr[j][1])
                        ans = max(ans, mem[j][i])

    # print(dp(0, n))
    for j in range(len(arr) + 1):
        for i in range(n, -1, -1):
            ext = (i // c0) * d0
            if mem[j][i] == -1:
                mem[j][i] = ext
            else:
                mem[j][i] += ext
            ans = max(ans, mem[j][i])
    print(ans)

if __name__ == '__main__':
    n, m, c0, d0 = arr_inp(1)
    staff, arr = [arr_inp(1) for i in range(m)], []

    for a in staff:
        arr.extend([[a[2], a[3]] for i in range(a[0] // a[1])])

    mem = [[-1 for i in range(n + 1)] for j in range(len(arr) + 1)]
    main()

#Copied

n,m,c,d=map(int,input().split())
dp=[[0 for i in range(n+1)] for j in range(m+1)]
for i in range(1,n+1):
    if(i<c):dp[0][i]=dp[0][i-1]
    else:dp[0][i]=max(dp[0][i-c]+d,dp[0][i-1])
for i in range(1,m+1):
    a,b,c,d=map(int,input().split())
    for j in range(1,n+1):
        if(j<c):
            dp[i][j]=dp[i-1][j]
        else:
            for k in range(a//b+1):
                if(k*c<=j):dp[i][j]=max(dp[i][j],dp[i-1][j-k*c]+k*d)
                else:break
print(dp[m][n])

mikla, types, c0, d0 = map(int, input().split())
pieejamais = [0];pildijumapaterins = [0];miklaspaterins = [0];cena = [0]
for recepte in range(types):
    a, b, c, d = map(int, input().split())
    pieejamais.append(a);pildijumapaterins.append(b);miklaspaterins.append(c);cena.append(d)

tabula = [[0 for t in range(types + 1)] for m in range(mikla + 1)]
for n in range(mikla + 1):
    tabula[n][0] = (n // c0) * d0
for miklasdaudz in range(1, mikla + 1):
    for pildijumi in range(1, types + 1):
        maxx = 0
        for k in range(pieejamais[pildijumi] // pildijumapaterins[pildijumi] + 1):
            if miklasdaudz - miklaspaterins[pildijumi] * k >= 0:
                izmantotamikla = k * miklaspaterins[pildijumi]
                atlikusimikla = miklasdaudz - izmantotamikla
                pelna = cena[pildijumi] * k
                s = tabula[atlikusimikla][pildijumi - 1]
                if pelna + s > maxx:
                    maxx = pelna + s
        tabula[miklasdaudz][pildijumi] = maxx
print(tabula[mikla][types])

import functools

# The first line contains 4 integers n, m, c0 and d0 (1 ≤ n ≤ 1000, 1 ≤ m ≤ 10, 1 ≤ c0, d0 ≤ 100).
# Lavrenty has n grams of dough as well as m different stuffing types
# he can make buns without stuffings. Each of such buns requires c0 grams of dough and it can be sold for d0 tugriks
N, M, c0, d0 = map(int, input().split())

# Each of the following m lines contains 4 integers. The i-th line contains numbers ai, bi, ci and di (1 ≤ ai, bi, ci, di ≤ 100)
#  he has ai grams left of the i-th stuffing. It takes exactly bi grams of stuffing i and ci grams of dough to cook a bun with the i-th stuffing.
#  Such bun can be sold for di tugriks
recipes = []
available_filling = [0]
filling_consumption = [0]
dough_consumption = [0]
price = [0]
for m in range(M):
    ai,bi,ci,di = map(int, input().split())
    available_filling.append(ai)
    filling_consumption.append(bi)
    dough_consumption.append(ci)
    price.append(di)
    rec = (ai,bi,ci,di)
    recipes.append(rec)

# Let create array dp by size n x m. dp[i][j] means maximum number of tugriks that the baker can earn
# if he used i grams of dough and cook buns with stuffings of types 1..j.
#
# Initially dp[i][0] is 0 for all i.
#
# You can easily calculate this dp:
# dp[i][j] = max{ dp[ i-c[j]*k ][ j-1 ] + d[j]*k } for every k from 0 to a[j]/b[j], for which i-c[j]*k>=0

dp = [[0 for m in range(M + 1)] for n in range (N + 1)]
for n in range(N+1):
    dp[n][0] = (n // c0) * d0

for dough in range(1, N+1):
    for fill_considered in range(1, M+1):
        m = 0
        for k in range(available_filling[fill_considered] // filling_consumption[fill_considered] + 1):
            if dough-dough_consumption[fill_considered]*k>=0:
               prevdough = dough - dough_consumption[fill_considered] * k
               prevstuff = fill_considered - 1
               addition = price[fill_considered] * k
               m = max(m, dp[prevdough][prevstuff] + addition)
        dp[dough][fill_considered] = m

print(dp[N][M])

import sys
input=sys.stdin.readline
n,m,c0,d0=map(int,input().split())
maxi=(n//c0)*d0
dp=[[0 for i in range(n+1)] for j in range(m+1)]
i=1
while i*c0<=n:
    dp[0][i*c0]=i*d0
    i+=1
for i in range(1,m+1):
    a,b,c,d=map(int,input().split())
    for j in range(n+1):
        k=0
        while k*c+j<=n and b*k<=a:
            dp[i][k*c+j]=max(dp[i][k*c+j],max(dp[i-1][k*c+j],dp[i-1][j]+k*d))
            k+=1
    for j in range(n+1):
        dp[i][j]=max(dp[i][j],dp[i-1][j])

for i in range(m+1):
    for j in range(n+1):
        maxi=max(maxi,dp[i][j])
print(maxi)

inp = lambda: map(int, input().split())

n, m, c0, d0 = inp()

a = [0]
b = [0]
c = [0]
d = [0]

for i in range(m):
  ai, bi, ci, di = inp()
  a.append(ai)
  b.append(bi)
  c.append(ci)
  d.append(di)

dp = [[0 for _ in range(n+1)] for _ in range(m+1)]

for i in range(n+1):
  dp[0][i] = (i//c0)*d0

for i in range(1, m+1):
  for j in range(1, n+1):
    for k in range((a[i]//b[i])+1):  #maximum buns made with stuffing
      if j - (k*c[i]) >= 0:  #array boundary check
        dp[i][j] = max(dp[i][j], dp[i-1][j-(k*c[i])] + k*d[i])

print(dp[m][n])

R = lambda: map(int, input().split())
n, m, c0, d0 = R()
a, b, c, d = [0], [0], [0], [0]
for i in range(m):
    t1, t2, t3, t4 = R()
    a.append(t1)
    b.append(t2)
    c.append(t3)
    d.append(t4)
dp = [[0] * (n + 1) for i in range(m + 1)]
for j in range(n + 1):
    dp[0][j] = j // c0 * d0
for i in range(1, m + 1):
    for j in range(1, n + 1):
        x = 0
        dp[i][j] = dp[i - 1][j]
        while j >= x * c[i] and a[i] >= b[i] * x:
            dp[i][j] = max(dp[i][j], dp[i - 1][j - x * c[i]] + x * d[i])
            x += 1
print(dp[m][n])

n,m,c0,d0=map(int,input().split()) # testo, kol nac, test bez nac, pribil
dp=[]
for i in range(n+1): dp.append(i//c0*d0)
for i in range(m):
    a,b,c,d=map(int,input().split())#ost nach, need nach, need tes, pribil
    for j in range(1,a//b+1):
        for k in range(n,c-1,-1):
            dp[k]=max(dp[k],dp[k-c]+d)
print(dp[n])

#!/usr/bin/env python3

n, m, c0, d0 = map(int, input().rstrip().split())
cnt, c, d = [n//c0], [c0], [d0]

for i in range(m):
    ai, bi, ci, di = map(int, input().rstrip().split())
    cnt_i = min(n//ci, ai//bi)
    cnt.append(cnt_i)
    c.append(ci)
    d.append(di)

def binarize(v):
    b = 0
    while (b << 1) + 1 <= v:
        b = (b << 1) + 1  # 111..
        yield (b + 1) >> 1  # 111... + 1 = 1000...

    if b < v:
        yield v - b

dp = [0] * (n+1)
for i in range(m+1):
    for sub_cnt in binarize(cnt[i]):
        dough, gain = sub_cnt * c[i], sub_cnt * d[i]
        for pos in range(n, dough-1, -1):
            dp[pos] = max(dp[pos], dp[pos-dough] + gain)

print(dp[n])

n,m,c,d=map(int,input().split())
ar=[0]*1005
for i in range(c,n+1):
    ar[i]=ar[i-c]+d
for i in range(m):
    a,b,c,d=map(int,input().split())
    for j in range(a//b):
        e=n
        while(e>=c):
            ar[e]=max(ar[e],ar[e-c]+d)
            e-=1
print(ar[n])

n,m,c0,d0 = [int(j) for j in input().split()]
nach = []
nach.append([0,0,c0,d0])
for i in range(m):
    nach.append([int(j) for j in input().split()])

profit = []
nabor = [[0] * (m+1) for i in range(n+1)]
profit = [0] * (n+1)
for nn in range(1,n+1):
    for j in range(m+1):
        if nn - nach[j][2] >= 0:
            if (nabor[nn - nach[j][2]][j] + 1) * nach[j][1] <= nach[j][0] and profit[nn-nach[j][2]]+nach[j][3] > profit[nn]:
                profit[nn] = profit[nn-nach[j][2]]+nach[j][3]
                for k in range(m+1):
                    nabor[nn][k] = nabor[nn - nach[j][2]][k]
                nabor[nn][j] += 1
MaxProfit = 0
for i in range(n+1):
    if MaxProfit < profit[i]:
        MaxProfit = profit[i]

print(MaxProfit)

n, m, c, d = map(int, input().split())

t = [(d / c, 1000, c, d)] + [0] * m

for i in range(1, m + 1):

    a, b, c, d = map(int, input().split())

    t[i] = (d / c, a // b, c, d)

t.sort(reverse = True)

s, p = [0], [0] * (n + 1)

for i in range(m + 1):

    x, k, c, d = t[i]

    for j in range(k):

        r = []

        for x in s:

            y = x + c

            if y > n: continue

            if p[y] < p[x] + d:

                p[y] = p[x] + d

                r.append(y)

        if not r: break

        s = r

    x, s = 0, [0]

    for i in range(1, n + 1):

        if p[i] > x:

            s.append(i)

            x = p[i]

        else: p[i] = x

print(p[n])

# Made By Mostafa_Khaled

n,m,c0,d0=map(int,input().split())
lst=[(d0/c0,1000,c0,d0)]
for _ in range(m):
    a,b,c,d=map(int,input().split())
    lst.append((d/c,a//b,c,d))
lst.sort(reverse=True)
ind,res=[0],[0]*(n+1)
for _,(x,k,c,d) in enumerate(lst):
    for i in range(k):
        new=[]
        for j,y in enumerate(ind):
            if y+c>n:continue
            if res[y]+d>res[y+c]:
                res[y+c]=res[y]+d
                new.append(y+c)
        if new==[]:break
        ind=new[:]
    ind,elem=[0],0
    for i,x in enumerate(res):
        if x>elem:
            elem=x
            ind.append(i)
        else:res[i]=elem
print(res[-1])

n, m, c, d = map(int, input().split())
arr = [0]*1010
for i in range(c, n+1):
    arr[i] = arr[i-c] + d
for l in range(m):
    a, b, c, d = map(int, input().split())
    for i in range(0, a//b):
        j=n
        while j >= c:
            arr[j] = max(arr[j], arr[j-c] + d)
            j -= 1
print(arr[n])

n,m,c,d=map(int,raw_input().split())
arr=[0]*1001
for i in range(c,n+1):
	arr[i]=arr[i-c]+d

for l in range(0,m):
	a,b,c,d=map(int,raw_input().split())
	for i in range(0,a/b):
		j=n
		while(j>=c):
			arr[j]=max(arr[j],arr[j-c]+d)
			j-=1
print arr[n]

import sys
infile = None
if len(sys.argv) > 1:
	infile = open(sys.argv[1],'rU')
def rd():
	if infile:
		return infile.readline()[0:-1]
	return raw_input()

n,m,c0,d0 = [int(i) for i in rd().split()]
cnt={}
c={}
d={}
cnt[0] = n/c0
c[0] = c0
d[0] = d0
for i in xrange(1,m+1):
	ai,bi,c[i],d[i] = [int(j) for j in rd().split()]
	cnt[i] = ai/bi

f={}
for h in xrange(0,n+1):
	f[h] = 0
for i in xrange(m+1):
	for h in xrange(n,-1,-1):
		k = 1
		while k <= cnt[i] and h - k * c[i] >= 0:
			f[h] = max(f[h], f[h - k * c[i]] + k * d[i])
			k += 1

print f[n]

# -*- coding: utf-8 -*-

import sys

data = sys.stdin.readlines()

n, m, c0, d0 = map(int, data[0].split())

a = [0]
b = [0]
c = [0]
d = [0]

for i in xrange(1, m + 1):
    da, db, dc, dd = map(int, data[i].split())
    a.append(da)
    b.append(db)
    c.append(dc)
    d.append(dd)

dp = []      # n x m
for i in xrange(0, n + 1): dp.append([ 0 for j in xrange(0, m+1)])

for i in xrange(0, n + 1):
    for j in xrange(1, m + 1):
        for k in xrange(0, a[j]/b[j] + 1):
            if i - c[j]*k >= 0:
                dp[i][j] = max(dp[i][j], dp[i-c[j]*k][j-1] + d[j]*k)

#for i in xrange(0, n):
#    for j in xrange(0, m+1):
#        print "%3s " % dp[i][j],
#    print
#print

tugrics = 0
for k in xrange(0, n + 1):
    tugrics = max(tugrics, dp[k][m] + ((n-k)/c0)*d0)

print tugrics

from sys import stdin
from math import floor

buf = []
for line in stdin:
    buf.append(line.strip())
buf.reverse()

def getints():
    return tuple([int(e) for e in buf.pop().split()])

n, m, c, d = getints()
dat = [0 for i in range(n+1)]
for k in range(n/c+1):
    dat[k*c] = k*d
for i in range(m):
    a, b, c, d = getints()
    for j in reversed(range(n)):
        for k in range(min((n-j)/c, a/b)+1):
            q = j+k*c
            dat[q] = max(dat[q], dat[j]+k*d)

print max(dat)

#!/usr/bin/env python
"""(c) gorlum0 [at] gmail.com"""
import itertools as it
from sys import stdin

for line in stdin:
    n, m, c0, d0 = map(int, line.split())

    xss = [map(int, next(stdin).split()) for _ in xrange(m)]
    xss.insert(0, [0]*4)
    a, b, c, d = zip(*xss)
    ## print a, b, c, d

    dp = [[0]*(m+1) for n in xrange(n+1)]
    for i in xrange(n+1):
        for j in xrange(1, m+1):
            dp[i][j] = max(dp[i-c[j]*k][j-1] + d[j]*k \
                            for k in xrange(a[j]//b[j]+1) if i-c[j]*k >= 0)
    print max(dp[k][m] + (n-k)//c0 * d0 for k in xrange(n+1))

from sys import stdin

n, m, c0, d0 = map(int, next(stdin).split())

xss = [map(int, next(stdin).split()) for _ in xrange(m)]
xss.insert(0, [0]*4)
a, b, c, d = zip(*xss)

dp = [[0]*(m+1) for n in xrange(n+1)]
for i in xrange(n+1):
    for j in xrange(1, m+1):
        dp[i][j] = max(dp[i-c[j]*k][j-1] + d[j]*k \
                        for k in xrange(a[j]//b[j]+1) if i-c[j]*k >= 0)
print max(dp[k][m] + (n-k)//c0 * d0 for k in xrange(n+1))

str = raw_input()
arr = [int(s) for s in str.split(' ')]
pir = range(arr[1])
ans = range(arr[0]+1)
for i in range(0, arr[1]):
   str = raw_input()
   pir[i] = [int(s) for s in str.split(' ')]
for i in range (0, arr[0]+1):
    ans[i] = (i / arr[2])*arr[3]

for j in range(0, arr[1]):
 mx = pir[j][0]/pir[j][1]
 for i in range(arr[0],-1, -1):
   if i / pir[j][2] < mx:
      am = i / pir[j][2]
   else:
      am = mx
   while am > 0:
      k = am * pir[j][2]
      if ans[i] < ans[i-k]+am*pir[j][3]:
         ans[i] = ans[i-k]+am*pir[j][3]
      am -= 1
print ans[arr[0]]

r=lambda:map(int,raw_input().split())
[n,m,c0,d0]=r()
cnt=[1000]
c=[c0]
d=[d0]
for i in range(m):
	[a,b,c1,d1]=r()
	cnt+=[a/b]
	c+=[c1]
	d+=[d1]
l=[-1]*(n+1)
l[0]=0
for i in range(m+1):
	for k in xrange(n,-1,-1):
		for j in xrange(cnt[i]+1):
			ind=k+j*c[i]
			if l[k]!=-1 and ind<=n:
				l[ind] = max(l[ind],l[k]+j*d[i])
print max(l)

n, m, c, d = map(int, raw_input().split())
arr = [0] * 1001
for i in range(c, n+1):
	arr[i] = arr[i-c] + d

for l in range(0, m):
	a, b, c, d = map(int, raw_input().split())
	for i in range(0, a/b):
		j = n
		while(j >= c):
			arr[j] = max(arr[j], arr[j - c] + d)
			j -= 1
print arr[n]

import sys # sys.exit() quit()
R = lambda: map(int, raw_input().split())
#sys.stdin = open('input.txt','r'); sys.stdout = open('output.txt','w')

v=[0] * 1010
n,m,c0,d0 = R()

for i in xrange(c0,n+1):
    v[i] = v[i-c0]+d0
a=[0]*20
b=[0]*20
c=[0]*20
d=[0]*20
for _ in xrange(m):
    a[_],b[_],c[_],d[_]=R()
    for i in xrange(a[_]/b[_]):
        for j in xrange(n,c[_]-1,-1):
            v[j]=max(v[j],v[j-c[_]]+d[_])
print v[n]

n, m, c, d = map(int, raw_input().split())
t = [(d / c, 1000, c, d)] + [0] * m
for i in range(1, m + 1):
    a, b, c, d = map(int, raw_input().split())
    t[i] = (float(d) / c, a / b, c, d)
t.sort(reverse = True)
s, p = [0], [0] * (n + 1)
for i in range(m + 1):
    x, k, c, d = t[i]
    for j in range(k):
        r = []
        for x in s:
            y = x + c
            if y > n: break
            if p[y] < p[x] + d:
                p[y] = p[x] + d
                r.append(y)
        if not r: break
        s = r
    x, s = 0, [0]
    for i in range(1, n + 1):
        if p[i] > x:
            s.append(i)
            x = p[i]
        else: p[i] = x
print p[n]

import sys
def read_values():
  return map(int,raw_input().split())

n,m,c0,d0=read_values()
a = [0]+[0]*m
b = [0]+[0]*m
c = [c0]+[0]*m
d = [d0]+[0]*m
for i in range(1,m+1):
  a[i],b[i],c[i],d[i]=read_values()

res = [[0]*(n+1) for i in range(m+1)]
for N in range(n+1):
  res[0][N] = d[0]*(N/c[0])

for i in range(1,m+1):
  num=0
  while num*b[i]<=a[i] and num*c[i]<=n:
    for N in range(num*c[i],n+1):
      res[i][N] = max(res[i][N], res[i-1][N-num*c[i]]+num*d[i])
    num+=1

print res[m][n]

n, m, c, d = map(int, raw_input().split())
arr = [0]*1010

for i in range(c, n+1):
	arr[i] = arr[i-c] + d

for l in range(m):
	#get each description
	a, b, c, d = map(int, raw_input().split())
	for i in range(0, a/b):
		j = n	#maximum dough that I can use is n
		while j >= c:
			arr[j] = max(arr[j], arr[j-c] + d)
			j -= 1

print arr[n]

n,m,c0,d0 = map(int, raw_input().strip().split())

z = [n] +  [0]*(m+1)
c = [c0] + [0]*(m+1)
d = [d0] + [0]*(m+1)
for i in range(1, m+1):
    a,b,c[i],d[i]=map(int, raw_input().strip().split())
    z[i] = a//b
ans = 0

# dp[j][i] := max gain up to i, using j grams of dough
# = max_{k from 0 up to max(z[i], j // c[i])} {k*d[i] + dp[j - k*c[i]][i-1], dp[j][i-1]}
dp = [[0] * (m+1) for _ in range(n+1)]
for j in range(n+1):
    dp[j][0] = (j//c[0])*d[0]
    for i in range(1, m+1):
        dp[j][i] = dp[j][i-1]
        for k in range(min(z[i], j // c[i])+1):
            g  = k*d[i] + dp[j-k*c[i]][i-1]
            dp[j][i] = max(g, dp[j][i])

print max([dp[j][m] for j in range(n+1)])

import sys
input = sys.stdin.readline

n, m, c_0, d_0 = map(int, input().split())

 # dp[grams_of_dough][1..j stuffings]
dp = [[0 for _ in range(m + 1)] for _ in range(n + 1)]

# grams left, grams required, dough required, sell price
stuffing = [(0, 1, 0, 0)] + [map(int, input().split()) for _ in range(m)]

for i in range(0, n + 1):
  for j in range(1, m + 1):
    # attempt to make k of j-stuffed thingies
    for k in range(stuffing[j][0] / stuffing[j][1] + 1):
      if i - stuffing[j][2] * k > -1:
        dp[i][j] = max(dp[i - stuffing[j][2] * k][j - 1] + stuffing[j][3] * k, dp[i][j])

ans = 0
# for row in dp: print row
for k in range(n):
  ans = max(ans, dp[k][m] + ((n - k) / c_0) * d_0)

print ans

from sys import stdin

def arr_inp(n):
    if n == 1:
        return [int(x) for x in stdin.readline().split()]
    elif n == 2:
        return [float(x) for x in stdin.readline().split()]
    else:
        return list(stdin.readline()[:-1])

n, m, c0, d0 = arr_inp(1)
staff, percent, ans = [arr_inp(1) for i in range(m)], [[0, d0 / c0]], 0

for i in range(m):
    percent.append([i + 1, staff[i][-1] / staff[i][-2]])

percent.sort(reverse=True, key=lambda x: x[1])

for i, j in percent:
    if i:
        val = min(staff[i - 1][0] // staff[i - 1][1], n // staff[i - 1][2])
        ans += staff[i - 1][-1] * val
        n -= val * staff[i - 1][2]
    else:
        ans += d0 * (n // c0)
        n -= (n // c0) * c0

    # print(n, i, ans)

print(ans)

import sys

sys.setrecursionlimit(10 ** 6)

def pyes_no(condition) :
  if condition :
    print ("YES")
  else :
    print ("NO")

def plist(a, s = ' ') :
  print (s.join(map(str, a)))

def rint() :
  return int(sys.stdin.readline())

def rints() :
  return map(int, sys.stdin.readline().split())

def rfield(n, m = None) :
  if m == None :
    m = n

  field = []
  for i in xrange(n) :
    chars = sys.stdin.readline().strip()
    assert(len(chars) == m)
    field.append(chars)
  return field

def pfield(field, separator = '') :
  print ('\n'.join(map(lambda x: separator.join(x), field)))

def check_field_equal(field, i, j, value) :
  if i >= 0 and i < len(field) and j >= 0 and j < len(field[i]) :
    return value == field[i][j]
  return None

def digits(x, p) :
  digits = []
  while x > 0 :
    digits.append(x % p)
    x //= p
  return digits

def modpower(a, n, mod) :
  r = a ** (n % 2)
  if n > 1 :
    r *= modpower(a, n // 2, mod) ** 2
  return r % mod

def gcd(a, b) :
  if a > b :
    a, b = b, a

  while a > 0 :
    a, b = b % a, a

  return b

n, m, c0, d0 = rints()
n += 1

prev = [0] * n
for i in range((n - 1) / c0 + 1) :
  prev[i * c0] = i * d0

for i in range(m) :
  new = prev[:]
  a, b, c, d = rints()
  for start in range(n) :
    for bake in range(1, min((n - start - 1) / c + 1, a / b + 1)) :
      new[start + bake * c] = max(new[start + bake * c], prev[start] + bake * d)

  prev = new
print prev[-1]

import sys
from sys import stdin, stdout
def R():
    return map(int, stdin.readline().strip().split())

n, m, c, d = R()

arr1 = []
for i in range(n//c):
    arr1.append((c, d))
for i in range(m):
    a, b, c, d = R()
    for j in range(min(a//b, n//c)):
        arr1.append((c, d))

dp = [[0 for i in range(n+1)] for i in range(len(arr1))]
if len(dp) == 0:
    print(0)
    exit()
for i in range(len(arr1)):
    c, d = arr1[i-1]
    for w in range(n+1):
        dp[i][w] = dp[i-1][w]
        if w >= c:
            if dp[i-1][w-c] + d > dp[i][w]:
                dp[i][w] = dp[i-1][w-c] + d
print(dp, arr1)
stdout.write(str(dp[-1][-1]))
# print(arr1)
# for i in dp:
#     print(i)

# n grams of dough
# m stuffings
# a[i] grams left of stuffing i
# b[i] grams needed
# c[i] grams of dough
# d[i] price
#
# without stuffing: (special case)
# a0 = infinite
# b0 = 0
# c0 grams of dough
# d0 price
# maximize price over all buns

# at each step a choice of 1..k of m-th stuffings or no stuffing
#
# IH: we know how to find the max profit for dough n-1 and stuffings S[]
#
def f(n, a, b, c, d):
    m = len(a)
    P = [[-1] * m for _ in range(n + 1)] # n * m

    def rec(weight, index):
        if index < 0: return 0

        # memoization
        if P[weight][index] != -1:
            return P[weight][index]

        profit = 0

        # we can create at most a[i] // b[i] stuffings
        stuffing, count = 0, 0
        while stuffing <= a[index]:
            remains = weight - (count * c[index])

            # not enough dough
            if remains < 0:
                break

            prev_profit = rec(remains, index - 1)

            profit = max(profit, prev_profit + count * d[index])

            # try more stuffing
            stuffing += b[index]
            count += 1

        return profit

    ans = rec(n, m - 1)
    print(ans)
    return ans

inf = float("inf")
A = [inf, 7,  12 ]
B = [1,   3,   3 ]
C = [2,   2,   1 ]
D = [1,  100, 10 ]
assert f(10, A, B, C, D) == 241

n, m, c0, d0 = map(int, input().split())
a, b, c, d = [inf], [0], [c0], [d0]
for _ in range(m):
    _a, _b, _c, _d = map(int, input().split())
    a.append(_a)
    b.append(_b)
    c.append(_c)
    d.append(_d)

ans = f(n, a, b, c, d)
print(ans)

from sys import stdin, setrecursionlimit
from collections import *
import threading

def arr_inp(n):
    if n == 1:
        return [int(x) for x in stdin.readline().split()]
    elif n == 2:
        return [float(x) for x in stdin.readline().split()]
    else:
        return list(stdin.readline()[:-1])

def dp(i, rem):
    if rem == 0:
        return 0
    if i >= len(arr):
        if rem:
            return d0 * (rem // c0)
        else:
            return 0

    if mem[i][rem] != -1:
        return mem[i][rem]

    ans1, ans2, ans3 = dp(i + 1, rem), 0, 0

    if rem - arr[i][0] >= 0:
        ans2 = arr[i][1] + dp(i + 1, rem - arr[i][0])
    if rem - c0 >= 0:
        ans3 = d0 + dp(i + 1, rem - c0)

    mem[i][rem] = max(ans1, ans2, ans3)
    return mem[i][rem]

def main():
    ans = 0
    for j in range(len(arr)):
        mem[j][n] = 0

    if arr:
        if arr[0][0] <= n:
            mem[0][n - arr[0][0]] = arr[0][1]

        for j in range(1, len(arr)):
            for i in range(n + 1):
                mem[j][i] = mem[j - 1][i]

                if i + arr[j][0] <= n:
                    if mem[j - 1][i + arr[j][0]] != -1:
                        mem[j][i] = max(mem[j][i], mem[j - 1][i + arr[j][0]] + arr[j][1])
                        ans = max(ans, mem[j][i])

    # print(dp(0, n))
    for j in range(len(arr) + 1):
        for i in range(n, -1, -1):
            ext = (i // c0) * d0
            if mem[j][i] != -1:
                mem[j][i] += ext
            ans = max(ans, mem[j][i])
    print(ans)

if __name__ == '__main__':
    n, m, c0, d0 = arr_inp(1)
    staff, arr = [arr_inp(1) for i in range(m)], []

    for a in staff:
        arr.extend([[a[2], a[3]] for i in range(a[0] // a[1])])

    mem = [[-1 for i in range(n + 1)] for j in range(len(arr) + 1)]
    main()

from sys import stdin, setrecursionlimit
from collections import *
import threading

def arr_inp(n):
    if n == 1:
        return [int(x) for x in stdin.readline().split()]
    elif n == 2:
        return [float(x) for x in stdin.readline().split()]
    else:
        return list(stdin.readline()[:-1])

def dp(i, rem):
    if rem == 0:
        return 0
    if i >= len(arr):
        if rem:
            return d0 * (rem // c0)
        else:
            return 0

    if mem[i][rem] != -1:
        return mem[i][rem]

    ans1, ans2, ans3 = dp(i + 1, rem), 0, 0

    if rem - arr[i][0] >= 0:
        ans2 = arr[i][1] + dp(i + 1, rem - arr[i][0])
    if rem - c0 >= 0:
        ans3 = d0 + dp(i + 1, rem - c0)

    mem[i][rem] = max(ans1, ans2, ans3)
    return mem[i][rem]

def main():
    ans = 0
    for j in range(len(arr)):
        mem[j][n] = 0

    if arr:
        mem[0][n - arr[0][0]] = arr[0][1]

        for j in range(1, len(arr)):
            for i in range(n + 1):
                mem[j][i] = mem[j - 1][i]

                if i + arr[j][0] <= n:
                    if mem[j - 1][i + arr[j][0]] != -1:
                        mem[j][i] = max(mem[j][i], mem[j - 1][i + arr[j][0]] + arr[j][1])
                        ans = max(ans, mem[j][i])

    # print(dp(0, n))
    for j in range(len(arr) + 1):
        for i in range(n, -1, -1):
            ext = (i // c0) * d0
            if mem[j][i] == -1:
                mem[j][i] = ext
            else:
                mem[j][i] += ext
            ans = max(ans, mem[j][i])
    print(ans)

if __name__ == '__main__':
    n, m, c0, d0 = arr_inp(1)
    staff, arr = [arr_inp(1) for i in range(m)], []

    for a in staff:
        arr.extend([[a[2], a[3]] for i in range(a[0] // a[1])])

    mem = [[-1 for i in range(n + 1)] for j in range(len(arr) + 1)]
    main()

from sys import stdin

def arr_inp(n):
    if n == 1:
        return [int(x) for x in stdin.readline().split()]
    elif n == 2:
        return [float(x) for x in stdin.readline().split()]
    else:
        return list(stdin.readline()[:-1])

n, m, c0, d0 = arr_inp(1)
staff, percent, ans = [arr_inp(1) for i in range(m)], [[0, d0 / c0]], 0

for i in range(m):
    percent.append([i + 1, staff[i][-1] / staff[i][-2]])

percent.sort(reverse=True, key=lambda x: x[1])

# print(percent)
for i, j in percent:
    if i:
        val = min(staff[i - 1][0] // staff[i - 1][1], n // staff[i - 1][2])
        ans += staff[i - 1][-1] * val
        n -= val * staff[i - 1][2]
    else:
        ans += d0 * (n // c0)
        n -= (n // c0) * c0

    # print(n, i, ans)

print(ans)

from sys import stdin, setrecursionlimit
from collections import *
import threading

def arr_inp(n):
    if n == 1:
        return [int(x) for x in stdin.readline().split()]
    elif n == 2:
        return [float(x) for x in stdin.readline().split()]
    else:
        return list(stdin.readline()[:-1])

def dp(i, rem):
    if rem == 0:
        return 0
    if i >= len(arr):
        if rem:
            return d0 * (rem // c0)
        else:
            return 0

    if mem[i][rem] != -1:
        return mem[i][rem]

    ans1, ans2, ans3 = dp(i + 1, rem), 0, 0

    if rem - arr[i][0] >= 0:
        ans2 = arr[i][1] + dp(i + 1, rem - arr[i][0])
    if rem - c0 >= 0:
        ans3 = d0 + dp(i + 1, rem - c0)

    mem[i][rem] = max(ans1, ans2, ans3)
    return mem[i][rem]

def main():
    ans = 0
    for i in range(len(arr)):
        mem[i][n] = 0

    for j in range(len(arr)):
        for i in range(n, -1, -1):

            if mem[j][i] != -1:
                if i - arr[j][0] >= 0:
                    mem[j + 1][i - arr[j][0]] = max(mem[j + 1][i - arr[j][0]], mem[j][i] + arr[j][1])
                    ans = max(ans, mem[j + 1][i - arr[j][0]])

                tem = i
                while tem - c0 >= 0:
                    tem -= c0
                    mem[j + 1][tem] = max(mem[j + 1][tem], mem[j + 1][tem + c0] + d0)
                    ans = max(ans, mem[j + 1][tem])

    # print(dp(0, n))
    if not arr:
        ans = d0 * (n // c0)
    print(ans)

if __name__ == '__main__':
    n, m, c0, d0 = arr_inp(1)
    staff, arr = [arr_inp(1) for i in range(m)], []

    for a in staff:
        arr.extend([[a[2], a[3]] for i in range(a[0] // a[1])])

    mem = [[-1 for i in range(n + 1)] for j in range(len(arr) + 1)]
    main()

from sys import stdin, setrecursionlimit
from collections import *
import threading

def arr_inp(n):
    if n == 1:
        return [int(x) for x in stdin.readline().split()]
    elif n == 2:
        return [float(x) for x in stdin.readline().split()]
    else:
        return list(stdin.readline()[:-1])

def dp(i, rem):
    if rem == 0:
        return 0
    if i >= len(arr):
        if rem:
            return d0 * (rem // c0)
        else:
            return 0

    if mem[i][rem] != -1:
        return mem[i][rem]

    ans1, ans2, ans3 = dp(i + 1, rem), 0, 0

    if rem - arr[i][0] >= 0:
        ans2 = arr[i][1] + dp(i + 1, rem - arr[i][0])
    if rem - c0 >= 0:
        ans3 = d0 + dp(i + 1, rem - c0)

    mem[i][rem] = max(ans1, ans2, ans3)
    return mem[i][rem]

def main():
    ans = 0
    for i in range(len(arr)):
        mem[i][n] = 0

    for j in range(len(arr)):
        for i in range(n, -1, -1):

            if mem[j][i] != -1:
                if i - arr[j][0] >= 0:
                    mem[j + 1][i - arr[j][0]] = max(mem[j + 1][i - arr[j][0]], mem[j][i] + arr[j][1])
                    ans = max(ans, mem[j + 1][i - arr[j][0]])

                tem = i
                while tem - c0 >= 0:
                    tem -= c0
                    mem[j + 1][tem] = max(mem[j + 1][tem], mem[j + 1][tem + c0] + d0)
                    ans = max(ans, mem[j + 1][tem])

    # print(dp(0, n))
    print(ans)

if __name__ == '__main__':
    n, m, c0, d0 = arr_inp(1)
    staff, arr = [arr_inp(1) for i in range(m)], []

    for a in staff:
        arr.extend([[a[2], a[3]] for i in range(a[0] // a[1])])

    mem = [[-1 for i in range(n + 1)] for j in range(len(arr) + 1)]

    setrecursionlimit(2000)
    threading.stack_size(102400000)
    thread = threading.Thread(target=main)
    thread.start()

import functools as ft
mikla, types, c0, d0 = map(int, input().split())
pieejamais = [0];pildijumapaterins = [0];miklaspaterins = [0];cena = [0]
for recepte in range(types):
    a, b, c, d = map(int, input().split())
    pieejamais.append(a);pildijumapaterins.append(b);miklaspaterins.append(c);cena.append(d)

@ft.lru_cache(maxsize=524288)
def izd(miklasdaudz, pildijumi):
    if miklasdaudz == 0:
        return 0
    if pildijumi == 0:
        return (miklasdaudz // c0) * d0
    maxx = 0
    for k in range(pieejamais[pildijumi] // pildijumapaterins[pildijumi] + 1):
        izmantotamikla = k * miklaspaterins[pildijumi]
        atlikusimikla = miklasdaudz - izmantotamikla
        pelna = cena[pildijumi] * k
        s = izd(atlikusimikla, pildijumi - 1)
        if pelna + s > maxx:
            maxx = pelna + s
    return maxx
print(izd(mikla, types))

import functools

# The first line contains 4 integers n, m, c0 and d0 (1 ≤ n ≤ 1000, 1 ≤ m ≤ 10, 1 ≤ c0, d0 ≤ 100).
# Lavrenty has n grams of dough as well as m different stuffing types
# he can make buns without stuffings. Each of such buns requires c0 grams of dough and it can be sold for d0 tugriks
N, M, c0, d0 = map(int, input().split())

# Each of the following m lines contains 4 integers. The i-th line contains numbers ai, bi, ci and di (1 ≤ ai, bi, ci, di ≤ 100)
#  he has ai grams left of the i-th stuffing. It takes exactly bi grams of stuffing i and ci grams of dough to cook a bun with the i-th stuffing.
#  Such bun can be sold for di tugriks
recipes = []
available_filling = [0]
filling_consumption = [0]
dough_consumption = [0]
price = [0]
for m in range(M):
    ai,bi,ci,di = map(int, input().split())
    available_filling.append(ai)
    filling_consumption.append(bi)
    dough_consumption.append(ci)
    price.append(di)
    rec = (ai,bi,ci,di)
    recipes.append(rec)

# Let create array dp by size n x m. dp[i][j] means maximum number of tugriks that the baker can earn
# if he used i grams of dough and cook buns with stuffings of types 1..j.
#
# Initially dp[i][0] is 0 for all i.
#
# You can easily calculate this dp:
# dp[i][j] = max{ dp[ i-c[j]*k ][ j-1 ] + d[j]*k } for every k from 0 to a[j]/b[j], for which i-c[j]*k>=0

@functools.lru_cache()
def dp(dough, fill_considered):
    if dough == 0:
        return 0
    if fill_considered == 0:
        return (dough // c0) * d0
    m = 0
    for k in range(available_filling[fill_considered] // filling_consumption[fill_considered] + 1):
        prevdough = dough - dough_consumption[fill_considered] * k
        prevstuff = fill_considered - 1
        addition = price[fill_considered] * k
        m = max(m, dp(prevdough, prevstuff) + addition)
    return m

print(dp(N, M))

R = lambda: map(int, input().split())
n, m, c0, d0 = R()
a, b, c, d = [0], [0], [0], [0]
for i in range(m):
    t1, t2, t3, t4 = R()
    a.append(t1)
    b.append(t2)
    c.append(t3)
    d.append(t4)
dp = [[0] * (n + 1) for i in range(m + 1)]
for j in range(n + 1):
    dp[0][j] = j // c0 * d0
for i in range(1, m + 1):
    for j in range(1, n + 1):
        x = 0
        while j > x * c[i] and a[i] >= b[i] * x:
            dp[i][j] = max(dp[i][j], dp[i - 1][j - x * c[i]] + x * d[i])
            x += 1
print(dp[m][n])

n,m,c0,d0=map(int,input().split()) # testo, kol nac, test bez nac, pribil
dp=[] # max kol deneg za index testa
for i in range(n+1): dp.append(i//c0*d0)
for i in range(m):
    a,b,c,d=map(int,input().split())#ost nach, need nach, need tes, pribil
    for k in range(n,c-1,-1):
        dp[k]=max(dp[k],dp[k-c]+d)
print(dp[n])

n, m, c, d = map(int, input().split())
t = [(d / c, 1000, 1, c, d)] + [0] * m
for i in range(1, m + 1):
    a, b, c, d = map(int, input().split())
    t[i] = (d / c, a, b, c, d)
t.sort(reverse = True)
i = p = 0
while i < m + 1:
    u, a, b, c, d = t[i]
    i += 1
    if n < c: continue
    k = a // b
    p += d * k
    n -= c * k
    if n < 0:
        k = (- 1 - n) // c + 1
        n += c * k
        p -= d * k
print(p)

# -*- coding: utf-8 -*-

import sys

data = sys.stdin.readlines()

n, m, c0, d0 = map(int, data[0].split())

a = [0]
b = [0]
c = [0]
d = [0]

for i in xrange(1, m + 1):
    da, db, dc, dd = map(int, data[i].split())
    a.append(da)
    b.append(db)
    c.append(dc)
    d.append(dd)

dp = []      # n x m
for i in xrange(0, n): dp.append([ 0 for j in xrange(0, m+1)])

for i in xrange(0, n):
    for j in xrange(1, m + 1):
        for k in xrange(0, a[j]/b[j] + 1):
            if i - c[j]*k >= 0:
                dp[i][j] = max(dp[i][j], dp[i-c[j]*k][j-1] + d[j]*k)

#for i in xrange(0, n):
#    for j in xrange(0, m+1):
#        print "%3s " % dp[i][j],
#    print
#print

tugrics = 0
for k in xrange(0, n):
    tugrics = max(tugrics, dp[k][m] + ((n-k)/c0)*d0)

print tugrics

# -*- coding: utf-8 -*-

import sys

data = sys.stdin.readlines()

n, m, c0, d0 = map(int, data[0].split())

a = [0]
b = [0]
c = [0]
d = [0]

for i in xrange(1, m + 1):
    da, db, dc, dd = map(int, data[i].split())
    a.append(da)
    b.append(db)
    c.append(dc)
    d.append(dd)

dp = []      # n x m
for i in xrange(0, n): dp.append([ 0 for j in xrange(0, m+1)])

for i in xrange(0, n):
    for j in xrange(1, m + 1):
        for k in xrange(0, a[j]/b[j] + 1):
            if i + 1 - c[j]*k >= 0:
                dp[i][j] = max(dp[i][j], dp[i-c[j]*k][j-1] + d[j]*k)

#for i in xrange(0, n):
#    for j in xrange(0, m+1):
#        print "%3s " % dp[i][j],
#    print
#print

tugrics = 0
for k in xrange(0, n):
    tugrics = max(tugrics, dp[k][m] + ((n-k)/c0)*d0)

print tugrics

# -*- coding: utf-8 -*-

import sys

data = sys.stdin.readlines()

n, m, c0, d0 = map(int, data[0].split())

a = []
b = []
c = []
d = []

for i in xrange(1, m + 1):
    da, db, dc, dd = map(int, data[i].split())
    a.append(da)
    b.append(db)
    c.append(dc)
    d.append(dd)

dp = []      # n x m
for i in xrange(0, n): dp.append([ 0 for j in xrange(0, m+1)])

for i in xrange(0, n):
    for j in xrange(0, m):
        for k in xrange(0, a[j]/b[j]):
            if i - c[j]*k >= 0:
                dp[i][j+1] = max(dp[i-c[j]*k][j] + d[j]*k, dp[i][j+1])

#for i in xrange(0, n):
#    for j in xrange(0, m+1):
#        print "%3s " % dp[i][j],
#    print

print

tugrics = 0
for k in xrange(0, n):
    tugrics = max(tugrics, dp[k][m] + ((n-k)/c0)*d0)

print tugrics

str = raw_input()
arr = [int(s) for s in str.split(' ')]
pir = []
ans = range(arr[1]+1)
ans[0] = []
for j in range(0, arr[0]+1):
   ans[0].append( (j / arr[2])*arr[3])
for i in range(1, arr[1]+1):
   str = raw_input()
   pir = [int(s) for s in str.split(' ')]
   ans[i] = []
   last = 0
   am = (pir[0]/pir[1])*pir[2]
   for j in range(0, arr[0]+1):
       if(j <= am):
           last = (j / pir[2])*pir[3]
           ans[i].append(last)
       else:
           ans[i].append(last)
taken = []
z = arr[0]
bigA = 0
while True:
   max = -1
   k = -1
   for i in range(0, arr[1]+1):
       b = True
       for j in taken:
           if j == i:
              b = False
              break
       if b == False:
          continue
       if max < ans[i][z]:
            max = ans[i][z]
            k = i
  # print "max", max
 #  print "k", k
   if k == -1:
         break
   taken.append(k)
   bigA += max
   t = -1
   for i in range(0,len(ans[k])):
       if ans[k][i] == max:
         z = z - i
         break
#print "z", z
print bigA

str = raw_input()
arr = [int(s) for s in str.split(' ')]
pir = range(arr[1])
ans = range(arr[0]+1)
for i in range(0, arr[1]):
   str = raw_input()
   pir[i] = [int(s) for s in str.split(' ')]
for i in range (0, arr[0]+1):
    ans[i] = (i / arr[2])*arr[3]

for j in range(0, arr[1]):
 am = pir[j][0]/pir[j][1]
 for i in range(arr[0],-1, -1):
   if i / pir[j][2] < am:
      am = i / pir[j][2]
   k = am * pir[j][2]
   if ans[i] < ans[i-k]+am*pir[j][3]:
      ans[i] = ans[i-k]+am*pir[j][3]
print ans[arr[0]]

str = raw_input()
arr = [int(s) for s in str.split(' ')]
pir = range(arr[1])
ans = range(arr[0]+1)
for i in range(0, arr[1]):
   str = raw_input()
   pir[i] = [int(s) for s in str.split(' ')]
for i in range (0, arr[0]+1):
    ans[i] = (i / arr[2])*arr[3]

for j in range(0, arr[1]):
 am = pir[j][0]/pir[j][1]
 for i in range(arr[0],-1, -1):
   if i / pir[j][2] < am:
      am = i / pir[j][0]
   k = am * pir[j][2]
   if ans[i] < ans[i-k]+am*pir[j][3]:
      ans[i] = ans[i-k]+am*pir[j][3]
print ans[arr[0]]

l = []
n, m, c, d = map(int, raw_input().split())
l.append([0, 0, c, d])
for _ in xrange(m):
    l.append(map(int, raw_input().split()))

l.sort(key = lambda x: float(x[3]) / x[2], reverse = True)
ans = 0
i = 0
while True:
    if l[i][0] >= l[i][1]:
        if n >= l[i][2]:
            l[i][0] -= l[i][1]
            n -= l[i][2]
            ans += l[i][3]
        else:
            break
    else:
        i += 1
print ans

n,m,c0,d0 = map(int, raw_input().strip().split())

z = [n] +  [0]*(m+1)
c = [c0] + [0]*(m+1)
d = [d0] + [0]*(m+1)
for i in range(1, m+1):
    a,b,c[i],d[i]=map(int, raw_input().strip().split())
    z[i] = a//b
    print z[i]
ans = 0

# dp[j][i] := max gain up to i, using j grams of dough
# = max_{k from 0 up to max(z[i], j // c[i])} {k*d[i] + dp[j - k*c[i]][i-1], dp[j][i-1]}
dp = [[0] * (m+1) for _ in range(n+1)]
for j in range(n+1):
    dp[j][0] = (j//c[0])*d[0]
    for i in range(1, m+1):
        dp[j][i] = dp[j][i-1]
        for k in range(min(z[i], j // c[i])+1):
            g  = k*d[i] + dp[j-k*c[i]][i-1]
            dp[j][i] = max(g, dp[j][i])

print max([dp[j][m] for j in range(n+1)])