#include <iostream>
#include <vector>
#include <utility>
#include <cmath>
#include <algorithm>
#include <queue>
using namespace std;

#define x first
#define y second

typedef pair<int,int> pii;

int C, W;
vector<pii> pole;
vector<vector<int> > edge;
vector<pii> edge_set;

vector<vector<int> > face;
vector<vector<int> > dual_e;
vector<pii> dual_edge_set;

vector<int> detect_f(pii start, int cur, int prev) {
	vector<int> res;
	if(pii(cur,prev) == start) {
		return res;
	}
	if(pii(-1,-1) == start)
		start = pii(cur,prev);

	int bx, by, cx, cy;
	double mn = 10.0;
	int nx = -1;
	bx = pole[prev].x;
	by = pole[prev].y;
	cx = pole[cur].x;
	cy = pole[cur].y;
	for(int i = 0; i < edge[cur].size(); i++) {
		if(edge[cur][i] != prev) {
			double theta, phi, ag;
			int ax, ay;
			ax = pole[edge[cur][i]].x;
			ay = pole[edge[cur][i]].y;
			theta = atan2(by - cy, bx - cx);
			phi   = atan2(ay - cy, ax - cx);
			ag = phi - theta + 4*M_PI;
			while(ag > 2*M_PI) ag -= 2*M_PI;
			if(ag < mn) {
				nx = edge[cur][i];
				mn = ag;
			}
		}
	}

	res = detect_f(start, nx, cur);
	res.push_back(cur);
	return res;
}

int face_indx(vector<int> f) {
	for(int i = 0; i < face.size(); i++) {
		int sz = face[i].size();
		if(face[i].size() == f.size()) {
			for(int j = 0; j < face[i].size(); j++) {
				bool flg = true;
				for(int k = 0; k < face[i].size() && flg; k++) {
					flg = flg && (face[i][(j+k)%sz] == f[k]);
				}
				if(flg) {
					return i;
				}
			}
		}
	}
	return -1;
}

void mkdual() {
	for(int i = 0; i < edge_set.size(); i++) {
		pii de, e = edge_set[i];
		for(int i_ = 0; i_ < 2; i_++) {
			vector<int> f = detect_f(pii(-1,-1), e.second, e.first);
			int indx;
			indx = face_indx(f);
			if(indx < 0) {
				indx = face.size();
				face.push_back(f);
			}
			de.first = indx;
			swap(e.first, e.second);
			swap(de.first, de.second);
		}
		dual_edge_set.push_back(de);
	}
	dual_e.resize(face.size());
	sort(dual_edge_set.begin(), dual_edge_set.end());
	dual_edge_set.erase(unique(dual_edge_set.begin(), dual_edge_set.end()), dual_edge_set.end());
	for(int i = 0; i < dual_edge_set.size(); i++) {
		dual_e[dual_edge_set[i].first].push_back(dual_edge_set[i].second);
		dual_e[dual_edge_set[i].second].push_back(dual_edge_set[i].first);
	}
}

int solve() {
	int ur = 0;
	for(int i = 0; i < pole.size(); i++) {
		if(pole[ur] < pole[i])
			ur = i;
	}
	int nx = -1;
	double mn_arg = 100;
	for(int i = 0; i < edge[ur].size(); i++) {
		double arg;
		arg = atan2(pole[edge[ur][i]].y - pole[ur].y,
				pole[edge[ur][i]].x - pole[ur].x) - M_PI / 2.0 + 4 * M_PI;
		while(arg > 2 * M_PI) arg -= 2 * M_PI;
		
		if(arg < mn_arg) {
			mn_arg = arg;
			nx = edge[ur][i];
		}
	}
	int start;
	vector<int> mnpath;
	priority_queue<pii> q;
	const int INF = 1e9;
	start = face_indx(detect_f(pii(-1,-1), nx, ur));
	mnpath.resize(face.size());
	for(int i = 0; i < mnpath.size(); i++) mnpath[i] = INF;
	q.push(pii(0,start));
	while(!q.empty()) {
		pii a = q.top(); q.pop();
		if(mnpath[a.second] > -a.first) {
			mnpath[a.second] = -a.first;
		}
		for(int i = 0; i < dual_e[a.second].size(); i++) {
			if(mnpath[dual_e[a.second][i]] > -a.first + 1) {
				mnpath[dual_e[a.second][i]] = -a.first + 1;
				q.push(pii(a.first -1, dual_e[a.second][i]));
			}
		}
	}
	int res = -1;
	for(int i = 0; i < mnpath.size(); i++) {
		res = max(res, mnpath[i]);
	}
	return res;
}

int main() {
	while(cin >> C >> W, C || W) {
		pole.clear();
		edge.clear();
		edge_set.clear();
		face.clear();
		dual_edge_set.clear();
		dual_e.clear();
		pole.resize(C);
		edge.resize(C);
		for(int i = 0; i < pole.size(); i++) {
			cin >> pole[i].x >> pole[i].y;
		}
		for(int i = 0; i < W; i++) {
			int a, b;
			cin >> a >> b; a--; b--;
			edge_set.push_back(pii(a,b));
			edge[a].push_back(b);
			edge[b].push_back(a);
		}
		mkdual();
		/*
		for(int i = 0; i < face.size(); i++) {
			for(int j = 0; j < face[i].size(); j++)
				cout << face[i][j] << " ";
			cout << endl;
		} cout << endl;
		// */
		cout << solve() << endl;
	}
}

Measured memory_bytes: 1300