#include <cstdio>
#include <cstdlib>
#include <cstring>
#include <iostream>
#include <vector>
#include <string>
#include <algorithm>
#include <stack>
#include <queue>
#include <set>
#include <map>
using namespace std;
#define MOD 1000000007
#define ADD(X,Y) ((X) = ((X) + (Y)%MOD) % MOD)
typedef long long i64; typedef vector<int> ivec; typedef vector<string> svec;

int N, M;

bool test(int x, int y)
{
	for (int i = N - 1; i >= 0; --i) {
		if ((x & (1 << i)) && !(y & (1 << i))) {
			return ((x ^ y) & ((1 << i) - 1)) == 0;
		}
	}
	return true;
}

i64 modpow(i64 a, i64 p)
{
	if (p == 0) return 1;
	i64 t = modpow(a, p / 2);
	t = t * t % MOD;
	if (p & 1) t = t * a % MOD;
	return t;
}
i64 dp[5050][5050];
i64 inv2[5050], pows[5050];

i64 solve2()
{
	i64 tbl[2][5050];
	i64 acc[5050];
	int t = 0;

	for (int i = 0; i <= M; ++i) tbl[t][i] = 1;
	for (int i = 1; i <= N; ++i) {
		for (int j = 0; j <= M; ++j) tbl[1 - t][j] = 0;
		for (int j = 0; j <= M; ++j) {
			acc[j] = tbl[t][j] * j % MOD * inv2[j + 1] % MOD;
		}
		for (int j = 1; j <= M; ++j) ADD(acc[j], acc[j - 1]);
		for (int j = 0; j <= M; ++j) {
			tbl[1 - t][j] = (j > 0 ? acc[j - 1] : 0) * pows[j] % MOD;
			ADD(tbl[1 - t][j], tbl[t][j] * (j + 1));
		}
		t = 1 - t;
	}
	return tbl[t][M];
}

i64 solve()
{
	for (int i = 0; i <= N; ++i) {
		for (int j = 0; j <= M; ++j) {
			if (i == 0 || j == 0) {
				dp[i][j] = 1;
				continue;
			}
			i64 tmp = 0;
			ADD(tmp, dp[i - 1][j] * (j + 1));
			for (int d = 2; d <= j; ++d) {
				ADD(tmp, dp[i - 1][j - d + 1] * (j - d + 1) % MOD * modpow(2, d - 2));
			}
			dp[i][j] = tmp;
		}
	}
	return dp[N][M];
}

int main()
{
	pows[0] = inv2[0] = 1;
	for (int i = 1; i <= 5000; ++i) {
		pows[i] = pows[i - 1] * 2 % MOD;
		inv2[i] = modpow(pows[i], MOD - 2);
	}
	scanf("%d%d", &N, &M);

	printf("%lld\n", solve2()); return 0;

	for (int x = 0; x < (1 << N); ++x) {
		for (int y = 0; y < (1 << N); ++y) {
			bool isok = true;
			for (int m = 0; m < (1 << N); ++m) {
				int xx = x & m, yy = y & m;
				if (xx > yy && __builtin_popcount(xx ^ yy) >= 2) isok = false;
			}
			if (isok != test(x, y)) puts("><");
//			if (isok) printf("%d %d\n", x, y);
		}
	}
	return 0;
}
