Problem: problem

Santa Claus came from the sky to JOI town this year as well. Since every house in JOI has children, this Santa Claus must give out presents to every house in JOI. However, this year the reindeer I am carrying is a little deaf and I can only get off the top of the building, so it seems that I have to devise a little route to distribute gifts to all the houses.

JOI Town is divided into north, south, east and west, and each section is a house, a church, or a vacant lot. There is only one church in JOI town. According to the following rules, Santa Claus and reindeer depart from the church, give out one gift to every house, and then return to the church.

* This year's reindeer is a little deaf, so it can only fly straight in either the north, south, east, or west, and cannot change direction in the air.
* You can pass freely over the house where you haven't handed out the presents yet. You can get off at a house that hasn't given out presents yet. Whenever I get home, I give out presents and then take off in either direction of north, south, east or west.
* At the house in JOI town, I spend Christmas night without the fireplace until Santa Claus arrives, but after Santa Claus takes off, I turn on the fireplace. When you turn on the fireplace, smoke comes out of the chimney, so you can't pass over the house where you've finished giving out presents.
* You can pass freely over the church. However, since worship is held in the church, you cannot go down to the church until you have distributed all the presents.
* You can pass freely over the vacant lot, but you cannot get off at the vacant lot.


Create a program that asks how many directions Santa Claus and reindeer can give gifts to, given the structure of the town as input.

input

The input consists of multiple datasets. Each dataset is given in the following format.

Each dataset has n + 1 rows. On the first line, the integer m (1 ≤ m ≤ 10) and the integer n (1 ≤ n ≤ 10) are written separated by a space. In each line from the 2nd line to the n + 1th line, m of 0, 1, or 2 are written, separated by a blank, and each represents the state of each section. If we write the i-th section from the north and the j-th section from the west as (i, j) (1 ≤ i ≤ n, 1 ≤ j ≤ m), the j-th value on the i + 1 line is If the lot (i, j) is a vacant lot, it will be 0, if it is a house, it will be 1, and if it is a church, it will be 2. The number of churches is 1, and the number of houses is 1 or more and 23 or less. However, in the input data for scoring, the number of directions to be distributed does not exceed 2000000.

When both m and n are 0, it indicates the end of input. The number of data sets does not exceed 5.

Input / output example

Input example


3 2
1 0 1
1 0 2
3 3
1 1 1
1 0 1
1 1 2
0 0


Output example


2
6


<image>


Figure: All 6 directions to the second input example (numbers indicate the order of distribution)

The above question sentences and the data used for the automatic referee are the question sentences created and published by the Japan Committee for Information Olympics and the test data for scoring.



output

For each dataset, an integer indicating how many directions to distribute gifts is output on one line.

Example

Input

3 2
1 0 1
1 0 2
3 3
1 1 1
1 0 1
1 1 2
0 0


Output

2
6

Solution (in CPP):

Solution:
#include <iostream>
#include <fstream>
#include <stdio.h>
#include <math.h>
#include <time.h>
#include <string>
#include <tuple>
#include <vector>
#include <map>
#include <unordered_map>
#include <list>
#include <set>
#include <stack>
#include <queue>
#include <cstdlib>
#include <algorithm>
#include <random>
#include <cassert>
using namespace std;
#define LL long long
#define MP(a, b) make_pair(a, b)
#define MMP(a, b, c) make_pair(make_pair(a, b), c)
#define MAX 1000000000
#undef INT_MIN
#undef INT_MAX
#define INT_MIN -2147483648
#define INT_MAX 2147483647
#define LL_MIN -9223372036854775808
#define LL_MAX 9223372036854775807
#define PI 3.14159265359

vector<pair<int,int> > house;
vector<pair<int,int>> way[23];
int ok[23];

int solve(int i, int j){
	if(i == (1<<house.size())-1) return ok[j];
	int ans = 0;
	if((i&(1<<j)) == 0) return 0;
	bool flg = true;
	for(int k=way[j].size()-1; k>=0; k--){
		if(way[j][k] == MP(-1,-1)){
			flg = true;
			continue;
		}
		if(flg == false) continue;
		if((i&way[j][k].second) == way[j][k].second && (i&(1<<way[j][k].first)) == 0){
			ans += solve(i+(1<<way[j][k].first), way[j][k].first);
			flg = false;
		}
	}
	return ans;
}

int main() {
	iostream::sync_with_stdio(false);

	START:
	
	int m,n;
	cin >> m >> n;
	if(n == 0 && m == 0) return 0;
	int a[10][10];
	house.clear();
	pair<int,int> kyokai;
	for (int i = 0; i < n; i++) {
		for (int j = 0; j < m; j++) {
			cin >> a[i][j];
			if(a[i][j] == 0) a[i][j] = -1; //空地
			else if(a[i][j] == 2){
				a[i][j] = -2; //教会
				kyokai = MP(i,j);
			}
			else{
				a[i][j] = house.size();
				house.push_back(MP(i,j));
			}
		}
	}

	//経路計算
	for(int i=0; i<house.size(); i++){
		way[i].clear();
		int x = house[i].first;
		int y = house[i].second;
		int tmp = 0;
		for(int j=x+1; j<n; j++){
			if(a[j][y] >= 0){
				way[i].push_back(MP(a[j][y],tmp));
				tmp += 1<<a[j][y];
			}
			
		}
		way[i].push_back(MP(-1,-1));
		tmp = 0;
		for(int j=x-1; j>=0; j--){
			if(a[j][y] >= 0){
				way[i].push_back(MP(a[j][y],tmp));
				tmp += 1<<a[j][y];
			}
		}
		way[i].push_back(MP(-1,-1));
		tmp = 0;
		for(int j=y+1; j<m; j++){
			if(a[x][j] >= 0){
				way[i].push_back(MP(a[x][j],tmp));
				tmp += 1<<a[x][j];
			}
		}
		way[i].push_back(MP(-1,-1));
		tmp = 0;
		for(int j=y-1; j>=0; j--){
			if(a[x][j] >= 0){
				way[i].push_back(MP(a[x][j],tmp));
				tmp += 1<<a[x][j];
			}
		}
	}

	//教会隣接家dp初期化
	for(int i=0; i<house.size(); i++){
		ok[i] = 0;
	}
	for(int i=kyokai.first+1; i<n; i++){
		if(a[i][kyokai.second] >= 0){
			ok[a[i][kyokai.second]] = 1;
		}
	}
	for(int i=kyokai.first-1; i>=0; i--){
		if(a[i][kyokai.second] >= 0){
			ok[a[i][kyokai.second]] = 1;
		}
	}
	for(int i=kyokai.second+1; i<m; i++){
		if(a[kyokai.first][i] >= 0){
			ok[a[kyokai.first][i]] = 1;
		}
	}
	for(int i=kyokai.second-1; i>=0; i--){
		if(a[kyokai.first][i] >= 0){
			ok[a[kyokai.first][i]] = 1;
		}
	}

	//最終的な答え
	int ans = 0;
	for(int i=kyokai.first+1; i<n; i++){
		if(a[i][kyokai.second] >= 0){
			ans += solve(1<<a[i][kyokai.second],a[i][kyokai.second]);
			break;
		}
	}
	for(int i=kyokai.first-1; i>=0; i--){
		if(a[i][kyokai.second] >= 0){
			ans += solve(1<<a[i][kyokai.second],a[i][kyokai.second]);
			break;
		}
	}
	for(int i=kyokai.second+1; i<m; i++){
		if(a[kyokai.first][i] >= 0){
			ans += solve(1<<a[kyokai.first][i],a[kyokai.first][i]);
			break;
		}
	}
	for(int i=kyokai.second-1; i>=0; i--){
		if(a[kyokai.first][i] >= 0){
			ans += solve(1<<a[kyokai.first][i],a[kyokai.first][i]);
			break;
		}
	}
	cout << ans << endl;
	
	goto START;

	return 0;
}