//marico el que lo lea
#include <iostream>
#include <cstdio>
#include <cstring>
#include <cmath>
#include <algorithm>
#include <vector>
#include <map>
#include <set>
#include <queue>
#include <stack>
#include <stdlib.h>
#include <assert.h>
using namespace std;

typedef long long ll;
typedef vector<int> vi;
typedef vector<ll> vll;
typedef pair<int, int> ii;

void fastIO() {std::ios_base::sync_with_stdio(0);cin.tie(0);cout.tie(0);}

#define pb push_back
#define all(obj) obj.begin(), obj.end()
#define ms(obj, val) memset(obj, val, sizeof(obj))
#define ms2(obj, val, sz) memset(obj, val, sizeof(obj[0])*sz)

#define fst first
#define snd second

template<typename T, typename U> inline void mnze(T &x, U y) {if(y < x) x = y;}
template<typename T, typename U> inline void mxze(T &x, U y) {if(x < y) x = y;}

void _scan( int &x ) { scanf("%d",&x); }
void _scan( long long &x ) { scanf("%lld",&x); }
void _scan( double &x ) { scanf("%lf",&x); }
void _scan( char &x ) { scanf(" %c",&x); }
void _scan( char *x ) { scanf("%s",x); }
void scan() {}
template<typename T, typename... U>
void scan( T& head, U&... tail ) { _scan(head); scan(tail...);}

template<typename T> void _dbg(const char* sdbg, T h)
	{ cerr<<sdbg<<"="<<h<<"\n"; }
template<typename T, typename... U> void _dbg(const char* sdbg, T h, U... t) {
	while(*sdbg != ',')cerr<<*sdbg++;
	cerr<<"="<<h<<","; _dbg(sdbg+1, t...);
}

#ifdef LOCAL
#define debug(...) _dbg(#__VA_ARGS__, __VA_ARGS__)
#define debugv(x) {{cerr <<#x <<" = "; FORE(_i, (x)) cerr <<*_i <<", "; cerr <<"\n"; }}
#define debuga(x, sz) {{cerr <<#x <<" = "; FOR(_i, 0, sz) cerr << x[_i] <<", "; cerr <<"\n"; }}
#else
#define debug(...) (__VA_ARGS__)
#define debugv(x)
#define debuga(x, sz)
#define cerr if(0)cout
#endif

////////////////////////////////////////////////////////////////////////////////
////////////////////////////////////////////////////////////////////////////////

const int MAXN = 1e5+5;
#define L first
#define R second

int n;
ii LR[MAXN];
bool on1[MAXN];

set<ii> Ls, Rs;

void ADD(int i){
	Ls.insert({LR[i].L, i});
	Rs.insert({LR[i].R, i});
}
void ERASE(int i){
	auto it = Ls.find({LR[i].L, i});
	Ls.erase(it);
	it = Rs.find({LR[i].R, i});
	Rs.erase(it);
}
int CURR(){
	assert((int) Ls.size());
	auto l = Ls.end(); l--;
	auto r = Rs.begin();
	return max(0, (r->first) - (l->first) + 1);
}

int easysolve(){
	int ans = LR[0].R-LR[0].L+1;
	int ans2 = LR[1].R-LR[1].L+1;
	for(int i=2; i<(int)n; i++) mxze(ans2, LR[i].R-LR[i].L+1);
	return ans+ans2;
}
int SZ(int i){
	return LR[i].R - LR[i].L + 1;
}

int supereasysolve(){
	for(int i=1; i<(int)n; i++) if(SZ(i) > SZ(0)) swap(LR[i], LR[0]);
	int mxl = LR[1].L;
	int mnr = LR[1].R;
	for(int i=2; i<(int)n; i++){
		mxze(mxl, LR[i].L);
		mnze(mnr, LR[i].R);
	}
	return SZ(0) + max(0, mnr - mxl + 1);
}

int main(){
	scan(n);
	for(int i=0; i<(int)n; i++)
		scan(LR[i].L, LR[i].R);


	int ans = supereasysolve();
	for(int i=1; i<(int)n; i++){
		if(LR[i].R < LR[0].R || (LR[i].R == LR[0].R && LR[i].L > LR[0].L))
			swap(LR[i], LR[0]);
	}
	for(int i=0; i<(int)n; i++) if(LR[i].L <= LR[0].L) on1[i] = true;
	for(int i=0; i<(int)n; i++) if(!on1[i]) ADD(i);

	if(Rs.size() == 0){
		mxze(ans, easysolve());
		printf("%d\n",ans);
		return 0;
	}
	mxze(ans, LR[0].R-LR[0].L+1 + CURR());
	vector<ii> ch;
	for(int i=1; i<(int)n; i++){
		if(LR[0].L < LR[i].L && LR[i].L <= LR[0].R){
			ch.pb({LR[i].L, i});
		}
	}
	sort(all(ch));
	for(int i=0; i<(int)ch.size(); i++){
		int j = ch[i].second, nl = ch[i].first;
		ERASE(j);
		if(Ls.size()){
			mxze(ans, LR[0].R-nl+1 + CURR());
		}
	}
	printf("%d\n",ans);
}


Measured memory_bytes: 11516