#include <bits/stdc++.h>
using namespace std;
void read(long long &result, vector<int> *primes = nullptr) {
  result = 1;
  for (int rep = 0; rep < 3; ++rep) {
    int value;
    scanf("%d", &value);
    result *= value;
    if (primes != nullptr) {
      for (int p = 2; p * p <= value; ++p)
        if (value % p == 0) {
          primes->push_back(p);
          do {
            value /= p;
          } while (value % p == 0);
        }
      if (value != 1) {
        primes->push_back(value);
        value = 1;
      }
    }
  }
  if (primes != nullptr) {
    sort(primes->begin(), primes->end());
    primes->resize(unique(primes->begin(), primes->end()) - primes->begin());
  }
}
long long solve(long long x, long long y, long long m, vector<int> &primes) {
  vector<long long> dontmults;
  for (int p : primes) {
    long long pexp = 1;
    while (pexp <= x / p && y % (pexp * p) == 0) {
      pexp *= p;
      if (m % pexp != 0) break;
    }
    if (m % pexp != 0) {
      dontmults.push_back(pexp);
    }
  }
  long long result = 0;
  for (int s = 0; s < (1 << dontmults.size()); ++s) {
    long long mult = 1;
    for (int i = 0; i < (int)dontmults.size(); ++i)
      if (s & (1 << i)) {
        if (mult <= x / dontmults[i])
          mult *= dontmults[i];
        else
          mult = x + 1;
      }
    if (__builtin_popcount(s) % 2 == 0)
      result += x / mult;
    else
      result -= x / mult;
  }
  return result;
}
vector<long long> get_divisors(long long num, vector<int> &primes) {
  vector<long long> result = {1};
  for (int p : primes)
    if (num % p == 0) {
      const int prev_result_size = result.size();
      long long pexp = 1;
      do {
        pexp *= p;
        num /= p;
        for (int i = 0; i < prev_result_size; ++i)
          result.push_back(result[i] * pexp);
      } while (num % p == 0);
    }
  return result;
}
long long divisors_up_to(long long m, long long limit, vector<int> &primes) {
  long long m0 = 1, m1 = 1;
  for (int i = (int)primes.size() - 1; i >= 0; --i)
    if (m % primes[i] == 0) {
      if (m0 <= m1) {
        do {
          m /= primes[i];
          m0 *= primes[i];
        } while (m % primes[i] == 0);
      } else {
        do {
          m /= primes[i];
          m1 *= primes[i];
        } while (m % primes[i] == 0);
      }
    }
  vector<long long> divm0 = get_divisors(m0, primes);
  vector<long long> divm1 = get_divisors(m1, primes);
  if (divm1.size() > divm0.size()) swap(divm0, divm1);
  sort(divm1.begin(), divm1.end());
  long long result = 0;
  for (long long div0 : divm0) {
    result +=
        upper_bound(divm1.begin(), divm1.end(), limit / div0) - divm1.begin();
  }
  return result;
}
int main() {
  int nt;
  scanf("%d", &nt);
  for (int t = 0; t < nt; ++t) {
    long long y, x, s;
    vector<int> y_primes;
    read(y, &y_primes);
    read(x);
    vector<int> m_primes;
    read(s, &m_primes);
    const long long m = 2 * s;
    if (find(m_primes.begin(), m_primes.end(), 2) == m_primes.end())
      m_primes.insert(m_primes.begin(), 2);
    long long result =
        solve(x, y, m, y_primes) + divisors_up_to(m, y, m_primes);
    printf("%lld\n", result);
  }
  return 0;
}
