/**
 * Задача "Морской бой"
 * Городская олимпиада школьников Санкт-Петербурга по программированию, 2009.
 * Авторы задачи: Федор Царев, Роман Сатюков.
 * Автор решения: Максим Буздалов.
 *
 * Корректное решение.
 * Для классификации использует сортировку - решение с хешированием работает до 8 секунд.
 */
import java.io.*;
import java.util.*;

public class sea_mb {
    static void myAssert(String msg, boolean exp) {
        if (!exp) {
            throw new AssertionError(msg);
        }
    }

    /**
     * Точка, она же корабль.
     * Помимо координат и номера флота, в точке хранится классфикационная информация.
     * Эта информация устанавливается в точки непосредственно перед классификацией.
     * Точки сравнимы друг с другом: сначала как-нибудь по классификационной информации,
     * а затем по положению на прямой.
     */
    static class MutablePoint implements Comparable<MutablePoint> {
        public int x, y;
        public final int f;

        public long vmul;
        public int rems;

        public MutablePoint(int x, int y, int f) {
            this.x = x;
            this.y = y;
            this.f = f;
        }

        public void set(int x, int y) {
            this.x = x;
            this.y = y;
        }

        public void move(int x, int y) {
            this.x += x;
            this.y += y;
        }

        public boolean sameClass(MutablePoint a) {
            return vmul == a.vmul && rems == a.rems;
        }

        public final int compareTo(MutablePoint a) {
            if (rems != a.rems) {
                return rems < a.rems ? -1 : 1;
            }
            if (vmul != a.vmul) {
                return vmul < a.vmul ? -1 : 1;
            }
            return x == a.x ? y - a.y : x - a.x;
        }

        public String toString() {
            return "(" + x + "; " + y + ")@" + f;
        }
    }

    static class Fleet {
        final int index;
        final MutablePoint[] pts;
        final int t, dx, dy;

        int size() {
            return pts.length;
        }

        void move(int times) {
            int ddx = dx * times;
            int ddy = dy * times;
            for (int i = 0; i < pts.length; ++i) {
                pts[i].move(ddx, ddy);
            }
        }

        Fleet(int index, BufferedReader input) throws IOException {
            this.index = index;
            StringTokenizer firstLine = new StringTokenizer(input.readLine());
            int n = Integer.parseInt(firstLine.nextToken());
            t = Integer.parseInt(firstLine.nextToken());
            dx = Integer.parseInt(firstLine.nextToken());
            dy = Integer.parseInt(firstLine.nextToken());

            myAssert("Ship count is out of bounds", 1 <= n && n <= 10000);
            myAssert("t is out of bounds", 1 <= t && t <= 10);
            myAssert("dx is out of bounds", -10 <= dx && dx <= 10);
            myAssert("dy is out of bounds", -10 <= dy && dy <= 10);
            myAssert("Extra tokens in the first line of fleet description", !firstLine.hasMoreTokens());

            pts = new MutablePoint[n];
            for (int i = 0; i < n; ++i) {
                StringTokenizer st = new StringTokenizer(input.readLine());
                int x = Integer.parseInt(st.nextToken());
                int y = Integer.parseInt(st.nextToken());
                pts[i] = new MutablePoint(x, y, index);
                myAssert("x[i] is out of bounds", -1000000000 <= x && x <= 1000000000);
                myAssert("y[i] is out of bounds", -1000000000 <= y && y <= 1000000000);
                myAssert("Extra tokens in the ship description", !st.hasMoreTokens());
            }
        }
    }

    static class AnswerHolder {
        private long time = -1;

        public void updateAnswer(long ans) {
            if (ans < 0) {
                throw new AssertionError();
            }
            if (time == -1) {
                time = ans;
            } else {
                time = Math.min(time, ans);
            }
        }

        public long answer() {
            return time;
        }
    }

    private static int gcd(int a, int b) {
        while (a != 0) {
            int t = b % a;
            b = a;
            a = t;
        }
        return b;
    }

    private static int lcm(int a, int b) {
        return a * b / gcd(a, b);
    }

    /**
     * В этом массиве происходит классификация точек и их сортировка по прямой.
     */
    static MutablePoint[] array = new MutablePoint[50000];

    /**
     * Решаем задачу для двух флотов, если они каждую секунду перемещаются
     * друг относительно друга на (adx, ady).
     */
    private static int solve(Fleet f, Fleet g, int adx, int ady) {
        /**
         * Копируем нужные точки в массив.
         */
        System.arraycopy(f.pts, 0, array, 0, f.pts.length);
        System.arraycopy(g.pts, 0, array, f.pts.length, g.pts.length);
        int count = f.pts.length + g.pts.length;
        /**
         * Устанавливаем точкам классификацию по прямой и по остатку.
         */
        for (int i = 0; i < count; ++i) {
            MutablePoint p = array[i];
            p.vmul = (long)p.x * ady - (long)p.y * adx;
            int remX = adx == 0 ? 0 : (p.x % adx + adx) % adx;
            int remY = ady == 0 ? 0 : (p.y % ady + ady) % ady;
            p.rems = (remX << 16) + remY;
        }
        /**
         * Сортируем: одновременно классификация и сортировка вдоль прямой.
         */
        Arrays.sort(array, 0, count);

        int minrvx = Integer.MAX_VALUE;
        int minrvy = Integer.MAX_VALUE;

        int sadx = Integer.signum(adx);
        int sady = Integer.signum(ady);

        for (int curr = 1; curr < count; ++curr) {
            MutablePoint prevP = array[curr - 1], currP = array[curr];
            /**
             * Если соседние точки из одного класса и из разных флотов,
             * их надо рассмотреть на предмет того, не являются ли они ответом.
             */
            if (prevP.f != currP.f && prevP.sameClass(currP)) {
                int dx = currP.x - prevP.x;
                int dy = currP.y - prevP.y;
                if (currP.f == f.index) {
                    dx = -dx;
                    dy = -dy;
                }
                /**
                 * Это условие означает, что при увеличении времени корабли догоняют друг друга,
                 * а не удаляются.
                 */
                if (Integer.signum(dx) == sadx && Integer.signum(dy) == sady || dx == 0 && dy == 0) {
                    minrvx = Math.min(minrvx, Math.abs(dx));
                    minrvy = Math.min(minrvy, Math.abs(dy));
                }
            }
        }

        if (minrvx == Integer.MAX_VALUE || minrvy == Integer.MAX_VALUE) {
            return -1;
        } else {
            int rx = adx == 0 ? 0 : minrvx / Math.abs(adx);
            int ry = ady == 0 ? 0 : minrvy / Math.abs(ady);
            return Math.max(rx, ry);
        }
    }

    /**
     * Решаем задачу для двух флотов.
     */
    private static void solve(Fleet f, Fleet g, AnswerHolder ans) {
        /**
         * Период, с которым повторяется картина ходов.
         */
        int period = lcm(f.t, g.t);
        int fTimes = period / f.t;
        int gTimes = period / g.t;
        /**
         * Относительное передвижение флотов за период равно (adx; ady).
         */
        int adx = fTimes * f.dx - gTimes * g.dx;
        int ady = fTimes * f.dy - gTimes * g.dy;
        /**
         * Эмулируем положения кораблей в первый период.
         */
        for (int t = 0; t < period; ++t) {
            boolean test = false;
            if (t % f.t == 0) {
                f.move(1);
                test = true;
            }
            if (t % g.t == 0) {
                g.move(1);
                test = true;
            }
            if (test) {
                /**
                 * Тестируем данное положение флотов при данном векторе перемещения.
                 */
                int a = solve(f, g, adx, ady);
                if (a != -1) {
                    ans.updateAnswer(1 + t + (long)a * period);
                }
            }
        }
        /**
         * Откатываем флоты обратно, потому что с ними еще будем работать.
         */
        f.move(-fTimes);
        g.move(-gTimes);
    }

    public static void main(String[] args) throws IOException {
        BufferedReader in = new BufferedReader(new FileReader("sea.in"));
        int n = 2;
        Fleet[] fleets = new Fleet[n];
        for (int i = 0; i < n; ++i) {
            fleets[i] = new Fleet(i, in);
        }

        AnswerHolder ans = new AnswerHolder();

        /**
         * Перебираем все пары флотов и обновляем ответ.
         */
        for (int f1 = 0; f1 < n; ++f1) {
            for (int f2 = f1 + 1; f2 < n; ++f2) {
                solve(fleets[f1], fleets[f2], ans);
            }
        }

        PrintWriter out = new PrintWriter("sea.out");
        out.println(ans.answer());
        out.close();
    }
}
