#include <iostream>
#include <sstream>
#include <string>
#include <algorithm>
#include <vector>
#include <stack>
#include <queue>
#include <set>
#include <map>
#include <cstdio>
#include <cstdlib>
#include <cstring>
#include <cmath>
#include <cassert>

using namespace std;

#define FOR(i,k,n) for(int i=(k); i<(int)(n); ++i)
#define REP(i,n) FOR(i,0,n)
#define FORIT(i,c) for(__typeof((c).begin())i=(c).begin();i!=(c).end();++i)

template<class T> void debug(T begin, T end){ for(T i = begin; i != end; ++i) cerr<<*i<<" "; cerr<<endl; }
inline bool valid(int x, int y, int W, int H){ return (x >= 0 && y >= 0 && x < W && y < H); }

typedef long long ll;
const int INF = 100000000;
const double EPS = 1e-8;
const int MOD = 1000000007;
int dx[8] = {1, 0, -1, 0, 1, -1, -1, 1};
int dy[8] = {0, 1, 0, -1, 1, 1, -1, -1};
#include <complex>
int sign(double x){
  if(x > EPS) return 1;
  if(x < -EPS) return -1;
  return 0;
}
typedef complex<double> Point;
double dot(Point a, Point b){
  return real(conj(a) * b);
}
double cross(Point a, Point b){
  return imag(conj(a) * b);
}
int ccw(Point a, Point b, Point c){
  b -= a; c -= a;
  if(cross(b, c) > EPS) return 1;
  if(cross(b, c) < -EPS) return -1;
  if(dot(b, c) < 0) return 2;
  if(norm(b) < norm(c)) return -2;
  return 0;
}
struct Line : public vector<Point> {
  Line(Point a, Point b){
    push_back(a); push_back(b);
  }
  Point vector() const {
    return back() - front();
  }
};
Point projection(Line l, Point p){
  double t = dot(p - l[0], l.vector()) / norm(l.vector());
  return l[0] + t * l.vector();
}
Point reflection(Line l, Point p){
  return p + 2.0 * (projection(l, p) - p);
}
Point crosspoint(Line l, Line m){
  double A = cross(l.vector(), m.vector());
  double B = cross(l.vector(), l[1] - m[0]);
  if(sign(A) == 0 && sign(B) == 0) return m[0];
  if(sign(A) == 0) return Point(1e8, 1e8);
  return m[0] + m.vector() * B / A;
}
bool intersectSP(Line s, Point p){
  return ccw(s[0], s[1], p) == 0;
}
vector<Line> mirrors;
Point start, goal;
vector<double> args;
void dfs(vector<int>& v){
  Point target = goal;
  for(int i = 0; i < v.size(); i++){
    target = reflection(mirrors[v[i]], target);
  }
  args.push_back(arg(target - start));
  if(v.size() < 5){
    for(int i = 0; i < mirrors.size(); i++){
      v.push_back(i);
      dfs(v);
      v.pop_back();
    }
  }
}
int main(){
  int N;
  int CASENUM = 1;
  while(cin >> N && N){
    //cerr << "CASE " << CASENUM++ << endl;
    mirrors.clear();
    REP(i, N){
      Point a[2];
      REP(j, 2) cin >> a[j].real() >> a[j].imag();
      mirrors.push_back(Line(a[0], a[1]));
    }
    cin >> start.real() >> start.imag() ;
    cin >> goal.real()  >> goal.imag();
    args.clear();
    vector<int> tmp;
    dfs(tmp);
    double ans = 1e8;
    sort(args.begin(), args.end());
    args.erase(unique(args.begin(), args.end()), args.end());
    REP(i, args.size()){
      //cerr << "------" << endl;
      Point curr = start;
      double ag = args[i];
      //fprintf(stderr, "ag = %f\n", ag);
      double dist = 0.0;
      bool ok = false;
      for(int iter = 0; iter < 6; iter++){
        //fprintf(stderr, "iter = %d curr = (%f, %f) go = (%f, %f)\n", iter, curr.real(), curr.imag(), polar(1.0, ag).real(), polar(1.0, ag).imag());
        vector<pair<double, int> > cand;
        if(sign(ag - arg(goal - curr)) == 0){
          //fprintf(stderr, "push (%f, -1)\n", abs(goal - curr));
          cand.push_back(make_pair(abs(goal - curr), -1));
        }
        for(int i = 0; i < mirrors.size(); i++){
          if(intersectSP(mirrors[i], curr)) continue;
          Point p = crosspoint(Line(curr, curr + polar(1.0, ag)), mirrors[i]);
          if(p == Point(1e8, 1e8)) continue;
          if(!intersectSP(mirrors[i], p)) continue;
          if(sign(arg(p - curr) - ag) != 0) continue;
          //fprintf(stderr, "push (%f, %d)\n", abs(p - curr), i);
          cand.push_back(make_pair(abs(p - curr), i));
        }
        sort(cand.begin(), cand.end());
        if(cand.empty()) break;
        //fprintf(stderr, "cand[0] = (%f, %d)\n", cand[0].first, cand[0].second);
        dist += cand[0].first;
        if(cand[0].second == -1){
          ok = true;
          break;
        }else{
          // update curr and ag
          Point next = curr + polar(cand[0].first, ag);
          ag = arg(next - reflection(mirrors[cand[0].second], curr));
          curr = next;
        }
      }
      //fprintf(stderr, "dist = %f\n", dist);
      if(ok) ans = min(ans, dist);
    }
    //assert(ans < 1e8);
    printf("%.12lf\n", ans);
  }
  return 0;
}

Measured memory_bytes: 1484