//桥:删掉之后,图就不连通
//边双连通分量:极大的不含有桥的连通块
//不管删掉哪条边,都是连通的
//任意两个点之间,至少存在两条不相交的路径
//割点:如果把某个点和它所关联的所有边都删掉,图就不连通
//每一个割点至少属于两个双连通分量
//点双连通分量:极大的不包含割点的连通块
//两个割点之间的边,不一定是桥
//一个桥的两个端点,不一定是桥
//边双连通分量不一定是点双连通分量
//点双连通分量不一定是边双连通分量
//找桥:x->y是桥 等价于 dfs(x)<low(y)
//找遍双连通分量:做法1:将所有桥删掉,
// 做法2:用一个栈,搜索完dfs(x)==low(x),那么当前还在栈中的其他点,就是双连通分量的其他点
//x--y
//如何判断是不是割点:当low(y)>=dfn(x),
// 1.如果x不是根节点,那么x就是割点 ,
// 2.如果x是根节点,那么至少存在两个y,low(y)>=dfn(x)
//如何求点的双连通分量:
//
//统计所有连通块个数cnt
//依此枚举从哪个块中删,删哪个点,可以把当前块儿分成s部分
//那么答案就是s+cnt-1的最大值
//那么就是找s
//用类似求割点的方法来做:
//如果dfn(x)<=low(y),那么如果把x删掉,y就会单独出来,那么就会多一个单独的子树,多一个块儿
//特判:如果x不是根节点,删掉之后就会有三部分(一般情况);如果是,删掉之后就会有两部分
//也就是枚举删除哪个割点
#include <cstdio>
#include <cstring>
#include <iostream>
#include <algorithm>
using namespace std;
const int N = 10050;
int n, m;
int h[N], e[N<<3], ne[N<<3], idx;
int dfn[N], low[N], timestamp;
//根节点,每个点删掉之后最多可以分为几块
int root;
inline int read()
{
int x_=0,f_=1;
char c_=getchar();
while(c_<'0'||c_>'9')
{
if(c_=='-') f_=-1;
c_=getchar();
}
while(c_>='0'&&c_<='9')
{
x_=(x_<<1)+(x_<<3)+c_-'0';
c_=getchar();
}
return x_*f_;
}
struct node
{
int id,w;
} ans[N];
void add(int a, int b)
{
e[idx] = b, ne[idx] = h[a], h[a] = idx ++ ;
}
void tarjan(int u)
{
dfn[u] = low[u] = ++ timestamp;
//当前块儿内已经可以分出来的子树的个数
int cnt = 0;
for (int i = h[u]; ~i; i = ne[i])
{
int j = e[i];
if (!dfn[j])
{
tarjan(j);
low[u] = min(low[u], low[j]);
//说明j走不到u上面
if (low[j] >= dfn[u])
{
cnt ++;
if(u!=root || cnt>1)
++ans[u].w;
}
}
//如果已经搜过了
else
low[u] = min(low[u], dfn[j]);
}
//如果u不是根节点,而且cnt大于0
//还要加上父节点的那一部分
if (u != root && cnt)
cnt ++ ;
//取大
}
inline bool cmp_(node aa,node bb)
{
if(aa.w==bb.w) return aa.id < bb.id;
return aa.w > bb.w;
}
int main()
{
while(~scanf("%d%d", &n, &m))
{
if(!n && !m)
return 0;
//初始化,有判重数组的作用
memset(dfn, 0, sizeof dfn);
memset(h, -1, sizeof h);
for(int i=1; i<=n; i++) ans[i]= {i,0};
idx = timestamp = 0;
while (1)
{
int a=read(), b=read();
if(a==-1 && b==-1)
break;
a++,b++;
add(a, b), add(b, a);
}
for(int i=1; i<=n; i++)
ans[i].id=i;
root=1;
tarjan(1);
sort(ans+1,ans+1+n,cmp_);
for(int i=1; i<=m; ++i)
printf("%d %d\n",ans[i].id-1,ans[i].w+1);
printf("\n");
}
return 0;
}