#include "bits/stdc++.h"
using namespace std;
using ll=int64_t;
using ld=long double;
using ull=unsigned long long;
template <class T>
using grid=vector<vector<T>>;
#define ALL(x) x.begin(),x.end()
#define rep(iter,from,to) for(ll iter=from;iter<to;++iter)

#ifndef ONLINE_JUDGE
#define local true;
#endif

const ll MOD = 1e9 + 7;
const ll INF = 1e17;
//#######################################################################
vector<vector<ll>> input(ll N, ll width) {
    string str;
    vector<vector<ll>> vec(N, vector<ll>(width));
    for (ll i = 0; i < N; ++i) {
        cin >> str;
        reverse(ALL(str));
        for (ll j = 0; j < width; ++j) {
            vec[i][j] = str.back();
            str.pop_back();
        }
    }
    return vec;
}
void op(vector<ll> vec) {
    ll size = (ll)vec.size();
    for (ll i = 0; i < size - 1; ++i) cout << vec[i] << " ";
    cout << vec.back() << endl;
}

void op(vector<vector<ll>> vec) {
    ll height = (ll)vec.size();
    ll width = (ll)vec[0].size();
    for (ll i = 0; i < height; ++i) {
        for (ll j = 0; j < width - 1; ++j) cout << vec[i][j] << " ";
        cout << vec[i].back() << endl;
    }
}
//########################################################################

struct in{
    ll len;
    string str;
    ll num;
};

bool compare(const in& fr, const in& se){
    if(fr.len!=se.len) return fr.len<se.len;
    else return fr.num>se.num;
}

int solve(){
    ll N,M;
    cin>>N>>M;
    random_device rnd;
    mt19937 mt(rnd());
    uniform_int_distribution<> pick(0,M-1);
    vector<in> dict;
    set<string> checker;
    in inserter;
    rep(i,0,M){
        string s;
        cin>>s;
        if(checker.count(s)==0){
            inserter.len=s.size();
            inserter.str=s;
            inserter.num=1;
            checker.insert(s);
            dict.push_back(inserter);
        }
        else {
            rep(c,0,dict.size()) if(dict[c].str==s) {dict[c].num++; break;}
        }
    }
    grid<char> res(N,vector<char>(N,'.'));
    sort(ALL(dict),compare);
    //if(local) for(auto a:dict) cout<<a.str<<" "<<a.num<<endl;
    ll iter=0;
    for(ll i=0;i<N;++i) {
        ll cnt=0;
        ll start=0;
        while(true) {
            rep(j,0,dict[iter].len) {
                if(cnt>=N) break;
                res[i][start+j]=dict[iter].str[j];
                cnt++;
            }
            iter++;
            if(iter>=dict.size()) iter-=dict.size();
            start+=dict[iter].len;
            if(cnt>=N-1) break;
        }
    }
    uniform_int_distribution<> rand7(0, 7);
    vector<char> alpha{'A','B','C','D','E','F','G','H'}; 
    rep(i,0,N) {
        rep(j,0,N) {
            if(res[i][j]=='.') res[i][j]=alpha[rand7(mt)];
            cout<<res[i][j];
        }
        cout<<endl;
    }
    return 0;
}


int main(void){
    std::cin.tie(nullptr);
	std::ios_base::sync_with_stdio(false);
	std::cout << std::fixed << std::setprecision(15);
	solve();
}

#pragma GCC target("avx")
#pragma GCC optimize("O3")
#pragma GCC optimize("unroll-loops")
#include <bits/stdc++.h>
//#include <atcoder/all>
#define rep(i, n) for (int i = 0; i < ll(n); ++i)
typedef int64_t lint;
using namespace std;
using ll = long long;
using P = pair<ll, ll>;
using lb = long double;

#define FOR(i, a, b) for (ll i = a; i <= (ll)(b); i++)
#define all(x) (x).begin(), (x).end()
#define MAX(x) *max_element(all(x))
#define MIN(x) *min_element(all(x))
#define debug(x) cerr << #x << ": " << x << "\n"
#define debugV(x)                              \
    for (int i = 0; i < ((ll)(x).size()); i++) \
    cerr << #x << "at:" << i << ": " << x[i] << "\n"
#define YES(c) cout << ((c) ? "YES\n" : "NO\n"), 0
#define Yes(c) cout << ((c) ? "Yes\n" : "No\n"), 0
#define O(p) cout << p << "\n", 0
#define OS(p) cout << p << " ", 0
#define ON(p) cout << p, 0
#define INF 1000000000000
#define MOD 1000000007
#define pb emplace_back
#define mp make_pair
#define F first
#define S second
#define CST(x) cout << fixed << setprecision(x)
#define uoset unordered_set
#define vec vector
#define str string
const int dy[4] = {-1, 0, 1, 0};
const int dx[4] = {0, 1, 0, -1}; //^>v<
const string dstr="URDL";

const int Dy[5]={0,-1, 0, 1, 0};
const int Dx[5]={0,0, 1, 0, -1};

struct RandomNumberGenerator
{
    mt19937 mt;

    RandomNumberGenerator() : mt(chrono::steady_clock::now().time_since_epoch().count()) {}

    int operator()(int a, int b)
    { // [a, b]
        uniform_int_distribution<int> dist(a, b);
        return dist(mt);
    }

    int operator()(int b)
    { // [0, b]
        return (*this)(0, b);
    }
};
struct Timer
{
    chrono::high_resolution_clock::time_point st;

    Timer() { reset(); }

    void reset()
    {
        st = chrono::high_resolution_clock::now();
    }

    chrono::milliseconds::rep elapsed()
    {
        auto ed = chrono::high_resolution_clock::now();
        return chrono::duration_cast<chrono::milliseconds>(ed - st).count();
    }
};

ll chatoi(char a)
{
    string s = "";
    s += a;
    return stoi(s);
}

//------------------------------------------------------------
ll N,M;


bool comp(const std::string& lh, const std::string& rh) {
     // 文字列lhの長さが文字列rhより短かったらtrueを返す
     return lh.length() < rh.length();
}

bool write(vec<str> &Mat,int piv,int sta,str &s,bool isX){
    if(isX){
        rep(i,s.size()){
            int x=(sta+i)%N;
            if(!(Mat[piv][x]=='.'||Mat[piv][x]==s[i])){
                return false;
            }
        }
    }else{
        rep(i,s.size()){
            int y=(sta+i)%N;
            if(!(Mat[y][piv]=='.'||Mat[y][piv]==s[i])){
                return false;
            }
        }
    }
    
    if(isX){
        rep(i,s.size()){
            int x=(sta+i)%N;
            Mat[piv][x]=s[i];
        }
    }else{
        rep(i,s.size()){
            int y=(sta+i)%N;
            Mat[y][piv]=s[i];
        }
    }
    return true;
}

//------------------------------------------------------------
int main()
{
    ios::sync_with_stdio(false);
    std::cin.tie(nullptr);
    //--------------------------------------------------------
    auto Rand=RandomNumberGenerator();
    auto Tim=Timer();
    
    cin>>N>>M;
    
    vec<str> Mat(N,"");
    vec<str> S(M);
    rep(i,N){
        rep(j,N){
            Mat[i]+='.';
        }
    }
    rep(i,M){
        str s;cin>>s;
        S[i]=s;
    }
    sort(all(S),comp);
    
    int y=0,x=0,Snow=0;
    while(Snow!=M){
        rep(i,N){
            rep(j,N){
                if(write(Mat,i,j,S[Snow],true)){
                    Snow++;
                    goto A;
                }else if(write(Mat,j,i,S[Snow],false)){
                    Snow++;
                    goto A;
                }
            }
        }
        Snow++;
        A:;
        if(Tim.elapsed()>2990){
            O("ASAS");
            break;
        }
    }
    
    
    rep(i,N){
        O(Mat[i]);
    }
    

    return 0;
}