#include <bits/stdc++.h>
#include <ext/pb_ds/assoc_container.hpp>
#include <ext/pb_ds/tree_policy.hpp>
using namespace std;
using namespace __gnu_pbds;
#define ordered_set <int, null_type, less<int>, rb_tree_tag, tree_order_statistics_node_update>
#define ordered_multiset <int, null_type, less_equal <int>, rb_tree_tag, tree_order_statistics_node_update>
#define double long double
#define pii pair <int, int>
#define tiii tuple <int, int, int>
#define tiiii tuple <int, int, int, int>
#define emb emplace_back
#define all(a) a.begin(), a.end()
#define rall(a) a.rbegin(), a.rend()
#define iShowSpeed cin.tie(NULL)->sync_with_stdio(false)
#define matrix vector <vector <int>>
#define mat(n, m) vector <vector <int>> (n, vector <int> (m));
const int mod = 1e9 + 7;
const int inf = 1e18;
const matrix II = {{1, 0}, {0, 1}};
const int N = 3e4 + 5;
vector <pii> adj[N];
set <int> mp[N];
void solve(){
int n, k; cin >> n >> k;
vector <pii> a(k);
for (auto &[pos, len] : a) {
cin >> pos >> len;
mp[pos].emplace(len);
}
a.resize(unique(a.begin(), a.end()) - a.begin());
for (auto &[pos, len] : a) {
int cnt = 0;
for (int i = pos + len; i < n; i += len) {
adj[pos].emb(++cnt, i);
if (mp[i].find(len) != mp[i].end()) break;
}
cnt = 0;
for (int i = pos - len; i >= 0; i -= len) {
adj[pos].emb(++cnt, i);
if (mp[i].find(len) != mp[i].end()) break;
}
}
priority_queue <pii, vector <pii>, greater <pii>> q; q.emplace(0, a[0].first);
vector <int> dis(n, inf); dis[a[0].first] = 0;
while (!q.empty()) {
auto [w, u] = q.top(); q.pop();
if (w > dis[u]) continue;
for (auto [ww, v] : adj[u]) {
// cout << u << " -> " << v << "\n";
int nw = w + ww;
if (nw < dis[v]) {
dis[v] = nw;
q.emplace(dis[v], v);
}
}
}
cout << (dis[a[1].first] == inf ? -1ll : dis[a[1].first]);
}
int32_t main(){
iShowSpeed;
// int q; cin >> q; while (q--)
solve();
}