#include <stdio.h>
#include <cmath>
#include <algorithm>
#include <cfloat>
#include <stack>
#include <queue>
#include <vector>
#include <string>
#include <iostream>
typedef long long int ll;
typedef unsigned long long int ull;
#define BIG_NUM 2000000000
#define MOD 1000000007
#define EPS 0.000000001
using namespace std;

#define NUM 1000030

enum DIR{
	N,
	E,
	S,
	W,
};

struct Info{
	int row,col;
};

bool* prime_table;
int** map;
Info* info;


int hole_num,start;
int diff_col[3] = {-1,0,1};
int diff_row_N[3] = {-1,0,0},diff_col_N[3] = {0,-1,1};
int diff_row_E[3] = {-1,0,1},diff_col_E[3] = {0,1,0};
int diff_row_S[3] = {0,0,1},diff_col_S[3] = {-1,1,0};
int diff_row_W[3] = {-1,0,1},diff_col_W[3] = {0,-1,0};

int dp[2][1101],last[1101];

void func(){

	for(int i = 0; i < 1101; i++){
		for(int k = 0; k < 2; k++)dp[k][i] = -1;
		last[i] = -1;
	}

	int row,col,next_col;

	row = info[start].row;
	col = info[start].col;

	if(prime_table[start]){
		dp[1][col] = 1;
		last[col] = start;
	}else{
		dp[1][col] = 0;
	}

	bool FLG;

	while(true){

		for(int col = 0; col < 1101; col++){
			dp[0][col] = dp[1][col];
		}

		row++;

		FLG = false;
		for(int col = 0; col < 1101; col++){
			if(dp[0][col] != -1){

				for(int i = 0; i < 3; i++){
					next_col = col + diff_col[i];
					if(map[row][next_col] > hole_num || map[row][next_col] == -1)continue;

					FLG = true;

					if(prime_table[map[row][next_col]]){
						if(dp[1][next_col] <= dp[0][col]+1){
							dp[1][next_col] = dp[0][col]+1;
							last[next_col] = map[row][next_col];
						}
					}else{

						if(dp[1][next_col] < dp[0][col]){
							dp[1][next_col] = dp[0][col];
							last[next_col] = last[col];
						}else if(dp[next_col] == dp[col]){
							last[next_col] = max(last[next_col],last[col]);
						}
					}
				}
			}
		}

		if(!FLG)break;
	}

	int ans1 = 0,ans2 = 0;

	for(int i = 0; i < 1101; i++){
		if(dp[0][i] > ans1){
			ans1 = dp[0][i];
			ans2 = last[i];
		}else if(dp[0][i] == ans1){
			ans2 = max(ans2,last[i]);
		}
	}

	printf("%d %d\n",ans1,ans2);

}

int main(){

	prime_table = new bool[NUM];

	for(int i = 0; i < NUM; i++){
		prime_table[i] = true;
	}

	prime_table[1] = false;

	int limit = sqrt(NUM);

	for(int i = 2; i <= limit; i++){
		if(prime_table[i]){
			for(int j = 2*i; j < NUM; j+=i){
				prime_table[j] = false;
			}
		}
	}

	map = new int*[1101];
	for(int i = 0; i < 1101; i++){
		map[i] = new int[1101];
		for(int k = 0; k < 1101; k++)map[i][k] = -1;
	}

	map[550][550] = 1;

	int row = 550,col = 550,adj_row,adj_col;
	int id = 2;
	DIR dir = E;

	bool FLG;

	while(id <= NUM){

		FLG = true;
		switch(dir){
		case N:
			row--;
			map[row][col] = id++;
			for(int i = 0; i < 3; i++){
				adj_row = row+diff_row_N[i];
				adj_col = col + diff_col_N[i];

				if(map[adj_row][adj_col] != -1){
					FLG = false;
					break;
				}
			}
			if(FLG)dir = W;

			break;
		case E:
			col++;
			map[row][col] = id++;
			for(int i = 0; i < 3; i++){
				adj_row = row+diff_row_E[i];
				adj_col = col + diff_col_E[i];

				if(map[adj_row][adj_col] != -1){
					FLG = false;
					break;
				}
			}
			if(FLG)dir = N;

			break;
		case S:
			row++;
			map[row][col] = id++;
			for(int i = 0; i < 3; i++){
				adj_row = row+diff_row_S[i];
				adj_col = col + diff_col_S[i];

				if(map[adj_row][adj_col] != -1){
					FLG = false;
					break;
				}
			}
			if(FLG)dir = E;

			break;
		case W:
			col--;
			map[row][col] = id++;
			for(int i = 0; i < 3; i++){
				adj_row = row+diff_row_W[i];
				adj_col = col + diff_col_W[i];

				if(map[adj_row][adj_col] != -1){
					FLG = false;
					break;
				}
			}
			if(FLG)dir = S;

			break;
		}
	}

	info = (Info*)malloc(sizeof(Info)*(NUM+1));

	for(int i = 0; i < 1101; i++){
		for(int k = 0; k < 1101; k++){
			if(map[i][k] != -1){
				info[map[i][k]].row = i;
				info[map[i][k]].col = k;
 			}
		}
	}

	while(true){
		scanf("%d %d",&hole_num,&start);
		if(hole_num == 0 && start == 0)break;

		func();
	}


	return 0;
}

Measured memory_bytes: 16748