#include <iostream>
#include <vector>
#include <algorithm>
#include <cstring>

using namespace std;

int N,M;
const int mod=1000000007;
const int MAX_V=1001;
typedef long long ll;

vector<int> G[MAX_V];
vector<int> rG[MAX_V];
bool used[MAX_V];
int cmp[MAX_V];
vector<int> vs;
vector<int> cG[MAX_V];
int in[1001];

void dfs(int s){
  used[s]=true;
  for(int i=0;i<G[s].size();i++){
    int to=G[s][i];
    if(!used[to])dfs(to);
  }
  vs.push_back(s);
}

void rdfs(int s,int k){
  used[s]=true;
  cmp[s]=k;
  for(int i=0;i<rG[s].size();i++){
    int to=rG[s][i];
    if(!used[to])rdfs(to,k);
  }
}

void makeGraph(int s){
  used[s]=true;
  for(int i=0;i<G[s].size();i++){
    int to=G[s][i];
    // 異なる連結成分へ移動
    if(cmp[to]!=cmp[s])
      cG[cmp[to]].push_back(cmp[s]);
    if(!used[to])makeGraph(to);
  }
}

int dp[1001];
int rec(int s){
  if(dp[s]>=0)return dp[s];
  ll res=1;
  for(int i=0;i<cG[s].size();i++){
    int to=cG[s][i];
    res=(res*(1+rec(to)))%mod;
  }
  return dp[s]=res%mod;
}

int main(){
  while(cin>>N>>M&&(N|M)){
    int S,D;
    for(int i=0;i<N;i++){
      G[i].clear();rG[i].clear();
      cG[i].clear();
    }
    for(int i=0;i<M;i++){
      cin>>S>>D;
      S--;D--;
      G[S].push_back(D);
      rG[D].push_back(S);
    }
    memset(used,0,sizeof(used));
    for(int i=0;i<N;i++)
      if(!used[i])dfs(i);
    memset(used,0,sizeof(used));
    int k=0;
    for(int i=vs.size()-1;i>=0;i--)
      if(!used[vs[i]])rdfs(vs[i],k++);
    // 連結成分を一つのノードとしたグラフを作成
    memset(used,0,sizeof(used));
    for(int i=0;i<N;i++)
      if(!used[i])makeGraph(i);
    memset(in,0,sizeof(in));
    for(int i=0;i<k;i++)
      for(int j=0;j<cG[i].size();j++)
	in[cG[i][j]]++;
    // 入点が存在しないところそれぞれについて計算
    memset(dp,-1,sizeof(dp));
    ll res=1;
    for(int i=0;i<k;i++)
      if(in[i]==0)res=(res*(1+rec(i)))%mod;
    cout<<res<<endl;
  }

  return 0;
}