You are given an H \times W grid. The square at the top-left corner will be represented by (0, 0), and the square at the bottom-right corner will be represented by (H-1, W-1).

Of those squares, N squares (x_1, y_1), (x_2, y_2), ..., (x_N, y_N) are painted black, and the other squares are painted white.

Let the shortest distance between white squares A and B be the minimum number of moves required to reach B from A visiting only white squares, where one can travel to an adjacent square sharing a side (up, down, left or right) in one move.

Since there are H × W - N white squares in total, there are _{(H×W-N)}C_2 ways to choose two of the white squares.

For each of these _{(H×W-N)}C_2 ways, find the shortest distance between the chosen squares, then find the sum of all those distances, modulo 1 000 000 007=10^9+7.

Constraints

* 1 \leq H, W \leq 10^6
* 1 \leq N \leq 30
* 0 \leq x_i \leq H-1
* 0 \leq y_i \leq W-1
* If i \neq j, then either x_i \neq x_j or y_i \neq y_j.
* There is at least one white square.
* For every pair of white squares A and B, it is possible to reach B from A visiting only white squares.

Input

Input is given from Standard Input in the following format:


H W
N
x_1 y_1
x_2 y_2
:
x_N y_N


Output

Print the sum of the shortest distances, modulo 10^9+7.

Examples

Input

2 3
1
1 1


Output

20


Input

2 3
1
1 2


Output

16


Input

3 3
1
1 1


Output

64


Input

4 4
4
0 1
1 1
2 1
2 2


Output

268


Input

1000000 1000000
1
0 0


Output

333211937
#include <bits/stdc++.h>

using namespace std;

#ifdef DEBUG_MODE
	#define DBG(n) n;
#else
	#define DBG(n) ;
#endif
#define REP(i,n) for(ll (i) = (0);(i) < (n);++i)
#define PB push_back
#define MP make_pair
#define FI first
#define SE second
#define SHOW1d(v,n) {for(int W = 0;W < (n);W++)cerr << v[W] << ' ';cerr << endl << endl;}
#define SHOW2d(v,i,j) {for(int aaa = 0;aaa < i;aaa++){for(int bbb = 0;bbb < j;bbb++)cerr << v[aaa][bbb] << ' ';cerr << endl;}cerr << endl;}
#define ALL(v) v.begin(),v.end()
#define Decimal fixed<<setprecision(20)
#define INF 1000000000
#define LLINF 1000000000000000000
#define MOD 1000000007

typedef long long ll;
typedef pair<ll,ll> P;

long long mod_div(long long a,long long b){
	if(a % b == 0)return a/b;
	long long tmp = MOD - 2,c = b,ret = 1;
	while(tmp > 0){
		if(tmp & 1){
			ret *= c;ret %= MOD;
		}
		c *= c;c %= MOD;tmp >>= 1;
	}
	return a*ret%MOD;
}

int n,h,w;
ll ans,distSum;
vector<pair<ll,ll>> v;
vector<ll> xx;
vector<ll> yy;

bool mp[111][111];
bool used[111][111];
ll dx[] = {1,0,-1,0};
ll dy[] = {0,1,0,-1};
ll couX[111];
ll couY[111];

void seicaAdd(ll &a,ll &b){
	a += b;
	if(a >= MOD)a -= MOD;
}

void makeTable(){
	yy.PB(0);
	yy.PB(h);
	xx.PB(0);
	xx.PB(w);
	
	REP(i,n){
		xx.PB(max(0LL,v[i].FI));
		xx.PB(max(0LL,v[i].FI+1));
		yy.PB(max(0LL,v[i].SE));
		yy.PB(max(0LL,v[i].SE+1));
	}
	
	sort(ALL(xx));
	sort(ALL(yy));
	
	xx.erase(unique(ALL(xx)),xx.end());
	yy.erase(unique(ALL(yy)),yy.end());
	
	REP(i,n){
		int x = lower_bound(ALL(xx),v[i].FI) - xx.begin();
		int y = lower_bound(ALL(yy),v[i].SE) - yy.begin();
		mp[y][x] = true;
		couX[x]++;
		couY[y]++;
	}	
		
	ll blackSum = 0;
	ll pointer = 0;
	REP(i,w){
		if(i == xx[pointer]){
			blackSum += couX[pointer];
			pointer++;
		}
		else{
			ll A = ((h * i % MOD) - blackSum + MOD) % MOD;
			ll B = ((h * (w - i) % MOD) - (n - blackSum) + MOD) % MOD;
			ll tmp = A * B % MOD;
			seicaAdd(ans,tmp);
		}
	}
	
	blackSum = 0;
	pointer = 0;
	REP(i,h){
		if(i == yy[pointer]){
			blackSum += couY[pointer];
			pointer++;
		}
		else{
			ll A = ((w * i % MOD) - blackSum + MOD) % MOD;
			ll B = ((w * (h - i	) % MOD) - (n - blackSum) + MOD) % MOD;
			ll tmp = A * B % MOD;
			seicaAdd(ans,tmp);
		}
	}
}

int main(){
	
	cin >> h >> w >> n;
	REP(i,n){
		int a,b;cin >> a >> b;
		v.PB(MP(b,a));
	}
	
	makeTable();
	
	REP(i,yy.size()-1){
		REP(j,xx.size()-1){
			if(!mp[i][j]){
				REP(ii,111)REP(jj,111)used[ii][jj] = false;
				ll nowMul = ((yy[i+1] - yy[i]) * (xx[j+1] - xx[j])) % MOD;
				queue<pair<pair<ll,ll>,ll>> que;
				que.push(MP(MP(i,j),0));
				used[i][j] = true;
				while(!que.empty()){
					auto now = que.front();que.pop();
					now.SE++;
					REP(k,4){
						ll y = now.FI.FI + dy[k];
						ll x = now.FI.SE + dx[k];
						if(x < 0 || y < 0 || x >= xx.size() - 1 || y >= yy.size() - 1)continue;
						if(mp[y][x] || used[y][x])continue;
						ll thisMul = (yy[y+1] - yy[y]) * (xx[x+1] - xx[x]) % MOD;
						ll tmp = (((nowMul * thisMul) % MOD) * now.SE) % MOD;
						seicaAdd(distSum,tmp);	
						que.push(MP(MP(y,x),now.SE));
						used[y][x] = true;
					}
				}
			}
		}
	}
	distSum = mod_div(distSum,2);
	cout << (ans + distSum) % MOD << endl;
	
	return 0;
}