#include <bits/stdc++.h>
using std::greater;
using std::map;
using std::max;
using std::min;
using std::multiset;
using std::sort;
int read() {
  char c = getchar();
  int h = 0;
  while (c < '0' || c > '9') c = getchar();
  while (c >= '0' && c <= '9') h = (h << 1) + (h << 3) + c - '0', c = getchar();
  return h;
}
const int MAXN = 100100;
const int p = 1000000007;
inline int add(int x, int y) { return x + y >= p ? x + y - p : x + y; }
int h, w, n;
namespace solve1 {
struct Node {
  int u, L, R, s;
  int num;
} a[MAXN];
int c1[MAXN];
int c2[MAXN];
map<int, int> qwq;
bool cmp1(int x, int y) { return a[x].u > a[y].u; }
bool cmp2(int x, int y) { return a[x].u + a[x].s > a[y].u + a[y].s; }
struct Segment_Tree {
  multiset<int, greater<int> > mx[MAXN * 4];
  void modify(int l, int r, int rt, int nowl, int nowr, int f, int flg) {
    if (nowl <= l && r <= nowr) {
      if (flg == 1)
        mx[rt].insert(f);
      else
        mx[rt].erase(mx[rt].find(f));
      return;
    }
    int mid = (l + r) >> 1;
    if (nowl <= mid) modify(l, mid, rt << 1, nowl, nowr, f, flg);
    if (nowr > mid) modify(mid + 1, r, rt << 1 | 1, nowl, nowr, f, flg);
  }
  int anss;
  void query(int l, int r, int rt, int pos) {
    if (mx[rt].size()) anss = max(anss, *mx[rt].begin());
    if (l == r) return;
    int mid = (l + r) >> 1;
    if (pos <= mid)
      query(l, mid, rt << 1, pos);
    else
      query(mid + 1, r, rt << 1 | 1, pos);
  }
  int Query(int pos) {
    anss = 0;
    query(1, w, 1, pos);
    return anss;
  }
} t;
int work1() {
  for (int i = 1; i <= n; i++) {
    a[i].u = read(), a[i].L = read(), a[i].R = read(), a[i].s = read();
    qwq[a[i].u] = i;
  }
  qwq[0] = n + 1;
  for (int i = 1; i <= n; i++) c1[i] = c2[i] = i;
  sort(c1 + 1, c1 + n + 1, cmp1);
  sort(c2 + 1, c2 + n + 1, cmp2);
  int ch2 = 0;
  while (ch2 + 1 <= n && a[c2[ch2 + 1]].u + a[c2[ch2 + 1]].s >= h + 1) {
    ch2++;
    t.modify(1, w, 1, a[c2[ch2]].L, a[c2[ch2]].R, a[c2[ch2]].u, 1);
  }
  t.modify(1, w, 1, 1, w, 0, 1);
  for (int i = 1; i <= w; i++) {
    int hh = t.Query(i);
    a[qwq[hh]].num = add(a[qwq[hh]].num, 1);
  }
  for (int i = 1; i <= n; i++) {
    Node X = a[c1[i]];
    while (ch2 + 1 <= n && a[c2[ch2 + 1]].u + a[c2[ch2 + 1]].s >= X.u) {
      ch2++;
      t.modify(1, w, 1, a[c2[ch2]].L, a[c2[ch2]].R, a[c2[ch2]].u, 1);
    }
    t.modify(1, w, 1, X.L, X.R, X.u, 0);
    if (X.L == 1) {
      int hh = t.Query(X.R + 1);
      a[qwq[hh]].num = add(a[qwq[hh]].num, add(X.num, X.num));
    } else if (X.R == w) {
      int hh = t.Query(X.L - 1);
      a[qwq[hh]].num = add(a[qwq[hh]].num, add(X.num, X.num));
    } else {
      int hh = t.Query(X.R + 1);
      a[qwq[hh]].num = add(a[qwq[hh]].num, X.num);
      hh = t.Query(X.L - 1);
      a[qwq[hh]].num = add(a[qwq[hh]].num, X.num);
    }
  }
  printf("%d\n", a[n + 1].num);
  return 0;
}
}  // namespace solve1
int main() {
  h = read(), w = read(), n = read();
  return solve1::work1();
}
