#include <bits/stdc++.h>
#ifdef __DEBUG__
    #define DBG(X) cout << #X << " = " << (X) << endl;
    #define SAY(X) cout << (X) << endl;
#else
    #define DBG(X)
    #define SAY(X)
#endif

using namespace std;

using ll = long long int;
using ull = unsigned long long int;
using ld = long double;
using pii = pair<int, int>;
using pll = pair<ll, ll>;

int dx[]={1, 0, -1, 0, 1,-1, 1,-1};
int dy[]={0, 1, 0, -1, 1, 1,-1,-1};
const int INT_INF = (int)(2e9);
const ll  LL_INF = (ll)(2e18);

inline void fast_io() { ios_base::sync_with_stdio(false); cin.tie(nullptr); cout.tie(nullptr); };
template<typename T, typename S> inline ostream& operator<<(ostream& os, const pair<T, S> p) { cout << "[" << p.first << ";" << p.second << "]"; return os; }
template<typename T, typename S> inline ostream& operator<<(ostream& os, const map<T, S> p) { for (auto el : p) cout << "[" << el.first << ";" << el.second << "]"; return os; }
template<typename T> inline ostream& operator<<(ostream& os, const vector<T>& v) { for (auto el : v) cout << el << " "; return os; }
template<typename T> inline ostream& operator<<(ostream& os, const deque<T>& v) { for (auto el : v) cout << el << " "; return os; }
template<typename T> inline ostream& operator<<(ostream& os, const set<T>& v) { for (auto el : v) cout << el << " "; return os; }
template<typename T> inline vector<T> fetch_vec(int sz) { vector<T> ret(sz); for (auto& elem : ret) cin >> elem; return ret; }

ll N,M;
struct L
{
    ll a,b,c;
    L(ll a, ll b, ll c):a(a),b(b),c(c){}
};
vector<L> Lh,Lv;
map<ll,ll> mapX,mapY;

void input(){
    fast_io();
    cin >> N >> M;
    mapX[0] = 0;
    mapY[0] = 0;
    for (ll i = 0; i < N; i++)
    {
        ll a,b,c; cin >> a >> b >> c;
        mapX[a] = 0;
        mapX[b] = 0;
        mapY[c] = 0;
        Lh.emplace_back(a,b,c);
    }

    for (ll i = 0; i < M; i++)
    {
        ll a,b,c; cin >> c >> a >> b;
        mapY[a] = 0;
        mapY[b] = 0;
        mapX[c] = 0;
        Lv.emplace_back(a,b,c);
    }
}

int solve(){
    vector<ll> xs,ys;
    for(auto& p:mapX){
        p.second = xs.size();
        xs.push_back(p.first);
    }
    for(auto& p:mapY){
        p.second = ys.size();
        ys.push_back(p.first);
    }
    ll h = xs.size()*2;
    ll w = ys.size()*2;
    vector<vector<int> > d(h,vector<int>(w,0));

    for (ll i = 0; i < N; i++)
    {
        ll a = mapX[Lh[i].a]*2;
        ll b = mapX[Lh[i].b]*2;
        ll c = mapY[Lh[i].c]*2;
        for (ll x = a; x <= b; x++) d[x][c] = -1;
    }
    
    for (ll i = 0; i < M; i++)
    {
        ll a = mapY[Lv[i].a]*2;
        ll b = mapY[Lv[i].b]*2;
        ll c = mapX[Lv[i].c]*2;
        for (ll y = a; y <= b; y++) d[c][y] = -1;
    }

    // pre-set

    queue<pll> q;
    ll source_x = mapX[0]*2;
    ll source_y = mapY[0]*2;
    q.emplace(source_x,source_y);
    d[source_x][source_y] = 1;
    while(!q.empty()){
        ll x = q.front().first;
        ll y = q.front().second;
        q.pop();
        for (int i = 0; i < 4; i++)
        {
            ll nx = x+dx[i];
            ll ny = y+dy[i];
            if(nx < 0 || nx >= h) continue;
            if(ny < 0 || ny >= w) continue;
            if(d[nx][ny]!=0) continue;
            d[nx][ny] = 1;
            q.emplace(nx,ny);
        }
    }

    ll ans = 0;
    for (ll i = 0; i < h; i++) for (ll j = 0; j < w; j++)
    {
        if(d[i][j]!=1) continue;
        if(i==0 || i==(h-1) || j==0 || j==(w-1) ) {cout << "INF" << endl; return 0;}
        if(i%2==0 || j%2==0) continue;
        ll ex = xs[i/2+1]-xs[i/2];
        ll ey = ys[j/2+1]-ys[j/2];
        ans += ex*ey;
    }
    cout << ans << endl;
    return 0;
}   

int main()
{
    input();
    solve();
    return 0;
}

Measured memory_bytes: 144708