#include<iostream>
#include<cstdio>
#include<algorithm>
#include<vector>
#define mod 1000000007
#define int long long
#define fi first
#define se second
using namespace std;
int poww(int a,int b)
{
	int ret=1;
	while(b)
	{
		if(b&1)
		{
			ret=ret*a%mod;
		}
		a=a*a%mod;
		b>>=1;
	}
	return ret;
}
int T,ID,n,k,id[200001],qzj[200001];
bool is[200001];
vector <pair<int,int> > g[200001];
struct edge
{
	int u,v;
}E[200001];
int ans,rt,rans,f[200001];
void dfs(int u,int fa)
{
//	cout<<u<<"\n";
	int son=0,noend=0;
	f[u]=1;
	for(pair<int,int> v:g[u])
	{
		if(v.fi==fa) continue;
		son++;
		dfs(v.fi,u);
		f[u]=f[u]*f[v.fi]%mod;
	}
	f[u]=f[u]*qzj[son]%mod;
}
void dfs2(int u,int fa,int ott)
{
//	cout<<u<<"\n";
	int tim=ott,son=0;
	for(pair<int,int> v:g[u])
	{
		if(v.fi==fa) continue;
		son++;
		tim=tim*f[v.fi]%mod;
	}
	int lef=1;
	for(pair<int,int> v:g[u])
	{
		if(v.fi==fa) continue;
		lef=0;
		if(is[v.se]&&v.se<rt) continue;
		dfs2(v.fi,u,tim*poww(f[v.fi],mod-2)%mod*qzj[son-1]%mod);
	}
	if(lef)
	{
//		cout<<rt<<' '<<u<<" : "<<ott<<"\n";
		ans=(ans+ott)%mod;
	}
}
signed main()
{
//	freopen("D:\\noip\\down\\day0\\traverse\\traverse1.in","r",stdin);
//	freopen("D:\\noip\\down\\day0\\traverse\\traverse1.out","w",stdout);
	freopen("traverse.in","r",stdin);
	freopen("traverse.out","w",stdout);
	ios::sync_with_stdio(false);
	cin.tie(0);
	cout.tie(0);
	cin>>ID>>T;
	qzj[0]=1;
	for(int i=1;i<=200000;i++)
	{
		qzj[i]=qzj[i-1]*i%mod;
	}
	while(T--)
	{
		ans=1;
		cin>>n>>k;
		for(int i=1;i<=n;i++)
		{
			g[i].clear();
			is[i]=false;
		}
		for(int i=1;i<n;i++)
		{
			cin>>E[i].u>>E[i].v;
			g[E[i].u].push_back({E[i].v,i});
			g[E[i].v].push_back({E[i].u,i});
		}
		for(int i=1;i<=k;i++)
		{
			cin>>id[i];
			is[id[i]]=1;
		}
		if(19<=ID&&ID<=21)
		{
			if(n==2)
			{
				cout<<1<<'\n';
				continue;
			}
			rans=0;
			int cancho=n-2;
			for(int i=1;i<=k;i++)
			{
				rans=(rans+qzj[n-3]*cancho)%mod;
//				cerr<<qzj[n-3]*cancho<<'\n';
				cancho--;
			}
			cout<<rans<<'\n';
			continue;
		}
		rans=0;
		for(int i=1;i<=k;i++)
		{
			int l=0,r=0;
			rt=id[i];
			dfs(E[id[i]].u,E[id[i]].v);
			dfs(E[id[i]].v,E[id[i]].u);
			ans=0;
			dfs2(E[id[i]].u,E[id[i]].v,1);
			l=ans;
			ans=0;
			dfs2(E[id[i]].v,E[id[i]].u,1);
			r=ans;
			rans=(rans+l*r)%mod;
		}
		cout<<(rans+mod)%mod<<'\n';
	}
}
/*
对于一条边
遍历到它时他的左边和右边会各选一个出来
k=1 怎么做？
对于一条边，他的儿子是一条链
我可以按任意顺序重排儿子，然后递归进子问题
相当于 \sum son! 

k=2？
为什么会算重？
两个点路径上儿子排列的首个点都是下一个点就算重了。
欸不是很对
在一棵树中： 
根的度为2
每一个的最后一个儿子度为2。 
那么你在最后你就算重了。 

我们不妨考虑给每种结果钦定一个根
不妨为编号最小的关键二度点
那么一个根成功的条件就是每个点子树重拍最后一个点不能是关键点且编号比自己小

一个 nk 做法。 
出了问题？ 
编号最小的不一定可以作为根
什么东西可以作为根？

好了。
赢了！

优化一步可以多 8 分。 
dsu 做到 nlog^2n
怎么感觉没什么分

1s 5e8 次取模？
人类能做到吗

我都累了。

拼个菊花 
*/
