#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-1));
		xx.PB(max(0LL,v[i].FI));
		xx.PB(max(0LL,v[i].FI+1));
		yy.PB(max(0LL,v[i].SE-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]++;
	}	
	
	/*
	SHOW1d(xx,xx.size());
	SHOW1d(yy,yy.size());
	SHOW1d(couX,xx.size());
	SHOW1d(couY,yy.size());
	SHOW2d(mp,yy.size(),xx.size());
	*/
	
	ll blackSum = 0;
	ll pointer = 0;
	REP(i,w){
		//cout << i << endl;
		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;
		//	cout << "A B tmp is "  << A << " " << B << " " << tmp << endl;
			seicaAdd(ans,tmp);
		}
	}
	
	blackSum = 0;
	pointer = 0;
	REP(i,h){
		//cout << i << endl;
		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;
			//cout << "A B tmp is "  << A << " " << B << " " << tmp << endl;
			seicaAdd(ans,tmp);
		}
	}
}

void tmpMakeTable(){
	REP(i,h+1)yy.PB(i);
	REP(i,w+1)xx.PB(i);
	REP(i,n){
		mp[v[i].SE][v[i].FI] = true;
	}
	SHOW1d(xx,xx.size());
	SHOW1d(yy,yy.size());
	SHOW2d(mp,yy.size(),xx.size());	
}

int main(){
	
	cin >> h >> w >> n;
	REP(i,n){
		int a,b;cin >> a >> b;
		v.PB(MP(b,a));
	}
	
	makeTable();
	//tmpMakeTable();
	
	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 << distSum << endl;
	//cout << ans << endl;
	cout << (ans + distSum) % MOD << endl;
	
	return 0;
}

Measured memory_bytes: 384