It's another Start[c]up finals, and that means there is pizza to order for the onsite contestants. There are only 2 types of pizza (obviously not, but let's just pretend for the sake of the problem), and all pizzas contain exactly S slices.

It is known that the i-th contestant will eat si slices of pizza, and gain ai happiness for each slice of type 1 pizza they eat, and bi happiness for each slice of type 2 pizza they eat. We can order any number of type 1 and type 2 pizzas, but we want to buy the minimum possible number of pizzas for all of the contestants to be able to eat their required number of slices. Given that restriction, what is the maximum possible total happiness that can be achieved?

Input

The first line of input will contain integers N and S (1 ≤ N ≤ 105, 1 ≤ S ≤ 105), the number of contestants and the number of slices per pizza, respectively. N lines follow.

The i-th such line contains integers si, ai, and bi (1 ≤ si ≤ 105, 1 ≤ ai ≤ 105, 1 ≤ bi ≤ 105), the number of slices the i-th contestant will eat, the happiness they will gain from each type 1 slice they eat, and the happiness they will gain from each type 2 slice they eat, respectively.

Output

Print the maximum total happiness that can be achieved.

Examples

Input

3 12
3 5 7
4 6 7
5 9 5


Output

84


Input

6 10
7 4 7
5 8 8
12 5 8
6 11 6
3 3 7
5 9 6


Output

314

Note

In the first example, you only need to buy one pizza. If you buy a type 1 pizza, the total happiness will be 3·5 + 4·6 + 5·9 = 84, and if you buy a type 2 pizza, the total happiness will be 3·7 + 4·7 + 5·5 = 74.
import java.io.OutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import java.io.PrintWriter;
import java.util.Arrays;
import java.io.BufferedWriter;
import java.io.IOException;
import java.io.InputStreamReader;
import java.util.StringTokenizer;
import java.io.Writer;
import java.io.OutputStreamWriter;
import java.io.BufferedReader;
import java.io.InputStream;

/**
 * Built using CHelper plug-in
 * Actual solution is at the top
 *
 * @author phantom11
 */
public class Main {
    public static void main(String[] args) {
        InputStream inputStream = System.in;
        OutputStream outputStream = System.out;
        InputReader in = new InputReader(inputStream);
        OutputWriter out = new OutputWriter(outputStream);
        TaskC solver = new TaskC();
        solver.solve(1, in, out);
        out.close();
    }

    static class TaskC {
        public void solve(int testNumber, InputReader in, OutputWriter out) {
            int N = in.nextInt(), S = in.nextInt(), i, j;
            long slicesA = 0, slicesB = 0;
            Items A[] = new Items[N], B[] = new Items[N];
            int countA = 0, countB = 0;
            long ans = 0;
            for (i = 0; i < N; i++) {
                long s = in.nextInt(), a = in.nextInt(), b = in.nextInt();
                if (a > b) {
                    //ans += (s / S) * S * a;
                    //s %= S;
                    A[countA++] = new Items(s, a, b, 1);
                    slicesA += s;
                } else {
                    //ans += (s / S) * S * b;
                    //s %= S;
                    B[countB++] = new Items(s, a, b, 2);
                    slicesB += s;
                }
            }
            Arrays.sort(A, 0, countA);
            Arrays.sort(B, 0, countB);
            //DebugUtils.debug(A, B, ans);
            i = 0;
            long numRemainingA = 0, numRemainingB = 0;
            while (i < countA && (slicesA >= S || numRemainingA > 0)) {
                if (numRemainingA > 0) {
                    long slicesUsed = Math.min(numRemainingA, A[i].s);
                    ans += A[i].a * slicesUsed;
                    slicesA -= slicesUsed;
                    numRemainingA -= slicesUsed;
                    A[i].s -= slicesUsed;
                    if (A[i].s > 0) {
                        i--;
                    }
                } else {
                    long slicesUsed = (A[i].s / S) * S;
                    if (slicesUsed > 0) {
                        ans += slicesUsed * A[i].a;
                        A[i].s -= slicesUsed;
                        slicesA -= slicesUsed;
                    }
                    if (slicesA >= S) {
                        ans += A[i].a * A[i].s;
                        numRemainingA = (S - A[i].s % S) % S;
                        slicesA -= A[i].s;
                        A[i].s = 0;
                    }
                }
                i++;
            }
            j = 0;
            while (j < countB && (slicesB >= S || numRemainingB > 0)) {
                if (numRemainingB > 0) {
                    long slicesUsed = Math.min(numRemainingB, B[j].s);
                    ans += B[j].b * slicesUsed;
                    slicesB -= slicesUsed;
                    numRemainingB -= slicesUsed;
                    B[j].s -= slicesUsed;
                    if (B[j].s > 0) {
                        j--;
                    }
                } else {
                    long slicesUsed = (B[j].s / S) * S;
                    if (slicesUsed > 0) {
                        ans += slicesUsed * B[j].b;
                        B[j].s -= slicesUsed;
                        slicesB -= slicesUsed;
                    }
                    if (slicesB >= S) {
                        ans += B[j].b * B[j].s;
                        numRemainingB = (S - B[j].s % S) % S;
                        slicesB -= B[j].s;
                        B[j].s = 0;
                    }
                }
                j++;
            }
            //DebugUtils.debug(A, B, ans);
//        numRemainingA %= S;
//        numRemainingB %= S;
//        if(numRemainingA > 0) {
//            numRemainingA = S - numRemainingA;
//        }
//        if(numRemainingB > 0) {
//            numRemainingB = S - numRemainingB;
//        }
//
//        for(i=0;i<countA;i++) {
//            if(A[i].s == 0 || numRemainingA == 0) continue;
//            long slicesUsed = Math.min(A[i].s, numRemainingA);
//            ans += A[i].a * slicesUsed;
//            A[i].s -= slicesUsed;
//            numRemainingA -= slicesUsed;
//            slicesA -= slicesUsed;
//        }
//        for(j=0;j<countB;j++) {
//            if(B[j].s == 0 || numRemainingB == 0) continue;
//            long slicesUsed = Math.min(B[j].s, numRemainingB);
//            ans += B[j].b * slicesUsed;
//            B[j].s -= slicesUsed;
//            numRemainingB -= slicesUsed;
//            slicesB -= slicesUsed;
//        }
            //DebugUtils.debug(A, B, ans);
            long sumA1 = 0, sumA2 = 0, sumB1 = 0, sumB2 = 0;
            for (i = 0; i < countA; i++) {
                if (A[i].s == 0) continue;
                sumA1 += A[i].a * A[i].s;
                sumA2 += A[i].b * A[i].s;
            }
            for (j = 0; j < countB; j++) {
                if (B[j].s == 0) continue;
                sumB1 += B[j].b * B[j].s;
                sumB2 += B[j].a * B[j].s;
            }
            //DebugUtils.debug(sumA1, sumA2, sumB1, sumB2);
            long max = Math.max(sumA1 + sumB2, sumB1 + sumA2);
            if (slicesA + slicesB <= S) {
                //only 1 pizza possible
                ans += max;
            } else {
                // both different types of pizza
                max = Math.max(max, sumA1 + sumB1);
                ans += max;
            }
            out.printLine(ans);
        }

        class Items implements Comparable<Items> {
            long s;
            long a;
            long b;
            long t;

            public Items(long s, long a, long b, long t) {
                this.s = s;
                this.a = a;
                this.b = b;
                this.t = t;
            }

            public int compareTo(Items x) {
                if (t == 1) {
                    return Long.compare(x.a - x.b, (this.a - this.b));
                } else {
                    return Long.compare(x.b - x.a, (this.b - this.a));
                }
            }

            public String toString() {
                return t + " " + s + " " + a + " " + b;
            }

        }

    }

    static class OutputWriter {
        private final PrintWriter writer;

        public OutputWriter(OutputStream outputStream) {
            writer = new PrintWriter(new BufferedWriter(new OutputStreamWriter(outputStream)));
        }

        public OutputWriter(Writer writer) {
            this.writer = new PrintWriter(writer);
        }

        public void print(Object... objects) {
            for (int i = 0; i < objects.length; i++) {
                if (i != 0)
                    writer.print(' ');
                writer.print(objects[i]);
            }
        }

        public void printLine(Object... objects) {
            print(objects);
            writer.println();
        }

        public void close() {
            writer.close();
        }

    }

    static class InputReader {
        BufferedReader in;
        StringTokenizer tokenizer = null;

        public InputReader(InputStream inputStream) {
            in = new BufferedReader(new InputStreamReader(inputStream));
        }

        public String next() {
            try {
                while (tokenizer == null || !tokenizer.hasMoreTokens()) {
                    tokenizer = new StringTokenizer(in.readLine());
                }
                return tokenizer.nextToken();
            } catch (IOException e) {
                return null;
            }
        }

        public int nextInt() {
            return Integer.parseInt(next());
        }

    }
}

