#!/usr/bin/env python3
# Copyright (C) 2017  Roland Lutz
#
# Permission to use, copy, modify, and/or distribute this software for any
# purpose with or without fee is hereby granted, provided that the above
# copyright notice and this permission notice appear in all copies.
#
# THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
# WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
# MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
# ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
# WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
# ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
# OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.

import getopt, os, re, sys
import icebox

GLB_NETWK_EXTERNAL_BLOCKS = [(13, 8, 1), (0, 8, 1), (7, 17, 0), (7, 0, 0),
                             (0, 9, 0), (13, 9, 0), (6, 0, 1), (6, 17, 1)]
GLB_NETWK_INTERNAL_TILES = [(7, 0), (7, 17), (13, 9), (0, 9),
                            (6, 17), (6, 0), (0, 8), (13, 8)]


## Get the global name of a net.
#
# \param x, y    coordinates of the tile to which the net belongs
# \param fw, fh  width and height of the tile fabric (excluding I/O tiles)
# \param net     net name
#
# \return the global name of the net if it is a span wire, otherwise
#         the unmodified net name
#
# There are 46624 span wires on the 1k (not counting dummies):
#
# span4_x[1..12]_g[1..20]_[0..11]
# span4_y[1..16]_g[1..16]_[0..11]
# span12_x[1..12]_g[1..28]_[0..1]
# span12_y[1..16]_g[1..24]_[0..1]
#
# span4_left_g[3..16]_[0..3]
# span4_right_g[5..18]_[0..3]
# span4_bottom_g[3..12]_[0..3]
# span4_top_g[5..14]_[0..3]
#
# span4_topleft[2,4,6,8]_[0..3]
# span4_bottomright[2,4,6,8]_[0..3]
#
# dummy_y[1..16]_g[0..3]_[0..11]
#
# "Dummy" nets are horizontal accesses to non-existing vertical span
# wires on the right edge which are listed by icebox but don't
# actually connect to anything outside the tile itself.

def translate_netname(x, y, fw, fh, net):
    def group_and_index(s, group_size):
        n = int(s)
        g = n // group_size
        i = n % group_size
        if g % 2 == 1:
            i = i + 1 - (i % 2) * 2
        return g, i

    # logic and RAM tiles

    match = re.match(r'sp4_h_r_(\d+)$', net)
    if match is not None:
        g, i = group_and_index(match.group(1), 12)
        return 'span4_y%d_g%d_%d' % (y, x - g + 4, i)
    match = re.match(r'sp4_h_l_(\d+)$', net)
    if match is not None:
        g, i = group_and_index(match.group(1), 12)
        return 'span4_y%d_g%d_%d' % (y, x - g + 3, i)

    match = re.match(r'sp4_v_b_(\d+)$', net)
    if match is not None:
        g, i = group_and_index(match.group(1), 12)
        return 'span4_x%d_g%d_%d' % (x, y + g, i)
    match = re.match(r'sp4_v_t_(\d+)$', net)
    if match is not None:
        g, i = group_and_index(match.group(1), 12)
        return 'span4_x%d_g%d_%d' % (x, y + g + 1, i)
    match = re.match(r'sp4_r_v_b_(\d+)$', net)
    if match is not None:
        g, i = group_and_index(match.group(1), 12)
        if x == fw:
            # this net doesn't connect anywhere
            return 'dummy_y%d_g%d_%d' % (y, g, i)
        else:
            return 'span4_x%d_g%d_%d' % (x + 1, y + g, i)

    match = re.match(r'sp12_h_r_(\d+)$', net)
    if match is not None:
        g, i = group_and_index(match.group(1), 2)
        return 'span12_y%d_g%d_%d' % (y, x - g + 12, i)
    match = re.match(r'sp12_h_l_(\d+)$', net)
    if match is not None:
        g, i = group_and_index(match.group(1), 2)
        return 'span12_y%d_g%d_%d' % (y, x - g + 11, i)

    match = re.match(r'sp12_v_b_(\d+)$', net)
    if match is not None:
        g, i = group_and_index(match.group(1), 2)
        return 'span12_x%d_g%d_%d' % (x, y + g, i)
    match = re.match(r'sp12_v_t_(\d+)$', net)
    if match is not None:
        g, i = group_and_index(match.group(1), 2)
        return 'span12_x%d_g%d_%d' % (x, y + g + 1, i)

    # I/O tiles

    match = re.match(r'span4_horz_(\d+)$', net)
    if match is not None:
        g, i = group_and_index(match.group(1), 12)
        if x == 0:
            return 'span4_y%d_g%d_%d' % (y, x - g + 4, i)
        else:
            return 'span4_y%d_g%d_%d' % (y, x - g + 3, i)

    match = re.match(r'span4_vert_(\d+)$', net)
    if match is not None:
        g, i = group_and_index(match.group(1), 12)
        if y == 0:
            return 'span4_x%d_g%d_%d' % (x, y + g + 1, i)
        else:
            return 'span4_x%d_g%d_%d' % (x, y + g, i)

    match = re.match(r'span12_horz_(\d+)$', net)
    if match is not None:
        g, i = group_and_index(match.group(1), 2)
        if x == 0:
            return 'span12_y%d_g%d_%d' % (y, x - g + 12, i)
        else:
            return 'span12_y%d_g%d_%d' % (y, x - g + 11, i)

    match = re.match(r'span12_vert_(\d+)$', net)
    if match is not None:
        g, i = group_and_index(match.group(1), 2)
        if y == 0:
            return 'span12_x%d_g%d_%d' % (x, y + g + 1, i)
        else:
            return 'span12_x%d_g%d_%d' % (x, y + g, i)

    # I/O tiles - peripheral wires

    match = re.match(r'span4_horz_r_(\d+)$', net)
    if match is not None:
        n = int(match.group(1)); g = n // 4; i = n % 4
        if y == 0:
            if fw - x + g - 4 < 0:
                return 'span4_bottomright%d_%d' % ((fw - x + 1 + g) * 2, i)
            elif x - g + 1 < 0:
                return 'span4_left_g%d_%d' % (-x + 1 + g, i)
            else:
                return 'span4_bottom_g%d_%d' % (x + 4 - g, i)
        else:
            if x - g - 1 < 0:
                return 'span4_topleft%d_%d' % ((x + 4 - g) * 2, i)
            elif x - g + 1 >= fw:
                return 'span4_right_g%d_%d' % (fh + fw - x + 1 + g, i)
            else:
                return 'span4_top_g%d_%d' % (x + 4 - g, i)

    match = re.match(r'span4_horz_l_(\d+)$', net)
    if match is not None:
        n = int(match.group(1)); g = n // 4; i = n % 4
        if y == 0:
            if x - g < 0:
                return 'span4_left_g%d_%d' % (-x + 2 + g, i)
            else:
                return 'span4_bottom_g%d_%d' % (x + 3 - g, i)
        else:
            if x - g - 2 < 0:
                return 'span4_topleft%d_%d' % ((x + 3 - g) * 2, i)
            else:
                return 'span4_top_g%d_%d' % (x + 3 - g, i)

    match = re.match(r'span4_vert_b_(\d+)$', net)
    if match is not None:
        n = int(match.group(1)); g = n // 4; i = n % 4
        if x == 0:
            if y + g - 3 < 0:
                return 'span4_bottom_g%d_%d' % (-y + 5 - g, i)
            if fh - y - g < 0:
                return 'span4_topleft%d_%d' % ((fh + 5 - y - g) * 2, i)
            else:
                return 'span4_left_g%d_%d' % (y + g, i)
        else:
            if y + g - 5 < 0:
                return 'span4_bottomright%d_%d' % ((y + g) * 2, i)
            elif y + g >= fh + 3:
                return 'span4_top_g%d_%d' % (fw + fh + 5 - y - g, i)
            else:
                return 'span4_right_g%d_%d' % (y + g, i)

    match = re.match(r'span4_vert_t_(\d+)$', net)
    if match is not None:
        n = int(match.group(1)); g = n // 4; i = n % 4
        if x == 0:
            if fh - y - g - 1 < 0:
                return 'span4_topleft%d_%d' % ((fh + 4 - y - g) * 2, i)
            else:
                return 'span4_left_g%d_%d' % (y + g + 1, i)
        else:
            if y + g >= fh + 2:
                return 'span4_top_g%d_%d' % (fw + fh + 4 - y - g, i)
            else:
                return 'span4_right_g%d_%d' % (y + g + 1, i)

    return net

## Return the human-readable name of the \c fabout net of IO tile
## <tt>(x, y)</tt>.

def lookup_fabout(x, y):
    if (x, y) in GLB_NETWK_INTERNAL_TILES:
        return 'glb_netwk_%d' % GLB_NETWK_INTERNAL_TILES.index((x, y))

    return 'fabout'


## Remove an argument from a LUT string and an associated list of
## argument names.
#
# This is a helper function for \ref lut_to_logic_expression.
#
# \param lut   string of 2^N `0' or `1' characters representing the
#              logic of an Nx1 look-up table
# \param args  list of N strings containing the human-readable names
#              of the arguments
# \param i     index of the argument to remove
# \param keep  boolean value indicating which value of the removed
#              argument is to be assumed in the resulting LUT
#
# \return a new pair <tt>(lut, args)</tt> with the argument removed

def discard_argument(lut, args, i, keep):
    assert len(lut) == 1 << len(args)
    assert i >= 0 and i < len(args)
    return ''.join(bit for j, bit in enumerate(lut)
                   if (j & (1 << i) != 0) == keep), \
           args[:i] + args[i + 1:]

## Negate a tuple representation of a logic expression.
#
# This is a helper function for \ref lut_to_logic_expression.

def negate_expr(expr):
    if len(expr) == 2:
        op, a = expr
        assert op == 'not'
        return a
    if len(expr) != 3:
        return 'not', expr
    a, op, b = expr
    if op == 'and':
        return negate_expr(a), 'or', negate_expr(b)
    if op == 'or':
        return negate_expr(a), 'and', negate_expr(b)
    assert op == 'xor'
    if len(a) == 2 and a[0] == 'not':
        return a[1], op, b
    if len(b) == 2 and b[0] == 'not':
        return a, op, b[1]
    return negate_expr(a), op, b

## Convert a tuple representation of a logic expression into a string.
#
# This is a helper function for \ref lut_to_logic_expression.
#
# \param expr        the expression to convert
# \param parenthize  whether a compound expression should be
#                    surrounded by parentheses

def stringify(expr, parenthize):
    if type(expr) == str:
        return expr
    assert type(expr) == tuple

    if len(expr) == 2:
        op, a = expr
        assert op == 'not'
        assert type(a) == str
        return "!" + a

    if len(expr) == 5:
        a, op0, b, op1, c = expr
        assert op0 == '?' and op1 == ':'
        s = '%s ? %s : %s' % (stringify(a, False), stringify(b, False),
                                                   stringify(c, False))
        if parenthize:
            return '(%s)' % s
        return s

    assert len(expr) == 3

    a, op, b = expr
    l = [a, b]
    i = 0
    while i < len(l):
        if type(l[i]) == tuple and len(l[i]) == 3 and l[i][1] == op:
            l = l[:i] + [l[i][0], l[i][2]] + l[i + 1:]
        else:
            i += 1

    if op == 'and':
        op = '&'
    elif op == 'xor':
        op = '^'
    elif op == 'or':
        op = '|'

    s = (' %s ' % op).join(stringify(x, True) for x in l)
    if parenthize:
        return '(%s)' % s
    return s

## Remove arguments which don't affect the result from a LUT string
## and an associated list of argument names.
#
# This is a helper function for \ref lut_to_logic_expression.
#
# \param lut   string of 2^N `0' or `1' characters representing the
#              logic of an Nx1 look-up table
# \param args  list of N strings containing the human-readable names
#              of the arguments
#
# \return a new pair <tt>(lut, args)</tt> with all unused arguments
#         removed

def discard_unused_arguments(lut, args):
    assert len(lut) == 1 << len(args)
    i = 0
    while i < len(args):
        diff = False
        for j in range(len(lut)):
            if j & (1 << i) == 0 and lut[j] != lut[j | (1 << i)]:
                diff = True
        if not diff:
            lut, args = discard_argument(lut, args, i, False)
        else:
            i += 1
    return lut, args

## Convert a LUT string to a logic expression.
#
# \param lut   string of 2^N `0' or `1' characters representing the
#              logic of an Nx1 look-up table
# \param args  list of N strings containing the human-readable names
#              of the arguments
#
# \return a string containing a human-readable logic expression
#         equivalent to the look-up table
#
# Example: lut_to_logic_expression('00010000', ['a', 'b', 'c']) -> 'a & b & !c'

def lut_to_logic_expression(lut, args):
    lut, args = discard_unused_arguments(lut, args)

    # filter out independent top-level arguments
    toplevel_args = []
    i = 0
    while i < len(args) and len(args) >= 2:
        ai_0 = set(bit for j, bit in enumerate(lut) if j & (1 << i) == 0)
        ai_1 = set(bit for j, bit in enumerate(lut) if j & (1 << i) != 0)
        assert len(ai_0) == 2 or len(ai_1) == 2

        if len(ai_0) == 1:
            # expression is constant if this argument is 0
            # e = (...) & arg  or  e = (...) | !arg
            if tuple(ai_0)[0] == '0':
                toplevel_args.append(('and', args[i]))
            else:
                toplevel_args.append(('or', ('not', args[i])))
            lut, args = discard_argument(lut, args, i, True)
            i = 0
            continue

        if len(ai_1) == 1:
            # expression is constant if this argument is 1
            # e = (...) & !arg  or  e = (...) | arg
            if tuple(ai_1)[0] == '0':
                toplevel_args.append(('and', ('not', args[i])))
            else:
                toplevel_args.append(('or', args[i]))
            lut, args = discard_argument(lut, args, i, False)
            i = 0
            continue

        i += 1

    i = 0
    while i < len(args) and len(args) >= 2:
        is_xor = True
        for j in range(len(lut)):
            if j & (1 << i) == 0 and lut[j] == lut[j | (1 << i)]:
                is_xor = False
                break

        if is_xor:
            toplevel_args.append(('xor', args[i]))
            lut, args = discard_argument(lut, args, i, False)
            continue

        i += 1

    # detect simple top-level ternary conditions
    i = 0
    while i < len(args) and len(args) >= 3:
        j = i + 1
        while j < len(args):
            ai_0_aj_0 = set(bit for k, bit in enumerate(lut)
                            if k & (1 << i) == 0 and k & (1 << j) == 0)
            ai_0_aj_1 = set(bit for k, bit in enumerate(lut)
                            if k & (1 << i) == 0 and k & (1 << j) != 0)
            ai_1_aj_0 = set(bit for k, bit in enumerate(lut)
                            if k & (1 << i) != 0 and k & (1 << j) == 0)
            ai_1_aj_1 = set(bit for k, bit in enumerate(lut)
                            if k & (1 << i) != 0 and k & (1 << j) != 0)
            assert len(ai_0_aj_0) == 2 or len(ai_0_aj_1) == 2 or \
                   len(ai_1_aj_0) == 2 or len(ai_1_aj_1) == 2

            if (len(ai_0_aj_0) == 2 or len(ai_0_aj_1) == 2) and \
               (len(ai_1_aj_0) == 2 or len(ai_1_aj_1) == 2) and \
               (len(ai_0_aj_0) == 2 or len(ai_1_aj_0) == 2) and \
               (len(ai_0_aj_1) == 2 or len(ai_1_aj_1) == 2):
                j += 1
                continue

            ai_doesnt_matter_for_aj_0 = True
            ai_doesnt_matter_for_aj_1 = True
            aj_doesnt_matter_for_ai_0 = True
            aj_doesnt_matter_for_ai_1 = True

            for k in range(len(lut)):
                if k & (1 << i) != 0 or k & (1 << j) != 0:
                    continue
                if lut[k] != lut[k | (1 << i)]:
                    ai_doesnt_matter_for_aj_0 = False
                if lut[k | (1 << j)] != lut[k | (1 << i) | (1 << j)]:
                    ai_doesnt_matter_for_aj_1 = False
                if lut[k] != lut[k | (1 << j)]:
                    aj_doesnt_matter_for_ai_0 = False
                if lut[k | (1 << i)] != lut[k | (1 << i) | (1 << j)]:
                    aj_doesnt_matter_for_ai_1 = False

            if len(ai_0_aj_0) == 1 and len(ai_0_aj_1) == 1 and \
                   aj_doesnt_matter_for_ai_1:
                assert tuple(ai_0_aj_0)[0] != tuple(ai_0_aj_1)[0]
                if tuple(ai_0_aj_0)[0] == '0':
                    toplevel_args.append((args[i], '?', ':', args[j]))
                else:
                    toplevel_args.append((args[i], '?', ':', ('not', args[j])))
                lut, args = discard_argument(lut, args, i, True)

                # break loops
                i = len(args)
                j = len(args)
                break

            if len(ai_1_aj_0) == 1 and len(ai_1_aj_1) == 1 and \
                   aj_doesnt_matter_for_ai_0:
                assert tuple(ai_1_aj_0)[0] != tuple(ai_1_aj_1)[0]
                if tuple(ai_1_aj_0)[0] == '0':
                    toplevel_args.append((args[i], '?', args[j], ':'))
                else:
                    toplevel_args.append((args[i], '?', ('not', args[j]), ':'))
                lut, args = discard_argument(lut, args, i, False)

                # break loops
                i = len(args)
                j = len(args)
                break

            if len(ai_0_aj_0) == 1 and len(ai_1_aj_0) == 1 and \
                   ai_doesnt_matter_for_aj_1:
                assert tuple(ai_0_aj_0)[0] != tuple(ai_1_aj_0)[0]
                if tuple(ai_0_aj_0)[0] == '0':
                    toplevel_args.append((args[j], '?', ':', args[i]))
                else:
                    toplevel_args.append((args[j], '?', ':', ('not', args[i])))
                lut, args = discard_argument(lut, args, j, True)

                # break loops
                i = len(args)
                j = len(args)
                break

            if len(ai_0_aj_1) == 1 and len(ai_1_aj_1) == 1 and \
                   ai_doesnt_matter_for_aj_0:
                assert tuple(ai_0_aj_1)[0] != tuple(ai_1_aj_1)[0]
                if tuple(ai_0_aj_1)[0] == '0':
                    toplevel_args.append((args[j], '?', args[i], ':'))
                else:
                    toplevel_args.append((args[j], '?', ('not', args[i]), ':'))
                lut, args = discard_argument(lut, args, j, False)

                # break loops
                i = len(args)
                j = len(args)
                break

            j += 1
        i += 1

    lut, args = discard_unused_arguments(lut, args)

    # group pairwise isolated arguments
    i = 0
    while i < len(args):
        j = i + 1
        while j < len(args):
            ai_doesnt_matter_for_aj_0 = True
            ai_doesnt_matter_for_aj_1 = True
            aj_doesnt_matter_for_ai_0 = True
            aj_doesnt_matter_for_ai_1 = True
            both_dont_matter_if_equal = True
            both_dont_matter_if_unequal = True

            for k in range(len(lut)):
                if k & (1 << i) != 0 or k & (1 << j) != 0:
                    continue
                if lut[k] != lut[k | (1 << i)]:
                    ai_doesnt_matter_for_aj_0 = False
                if lut[k | (1 << j)] != lut[k | (1 << i) | (1 << j)]:
                    ai_doesnt_matter_for_aj_1 = False
                if lut[k] != lut[k | (1 << j)]:
                    aj_doesnt_matter_for_ai_0 = False
                if lut[k | (1 << i)] != lut[k | (1 << i) | (1 << j)]:
                    aj_doesnt_matter_for_ai_1 = False
                if lut[k] != lut[k | (1 << i) | (1 << j)]:
                    both_dont_matter_if_equal = False
                if lut[k | (1 << i)] != lut[k | (1 << j)]:
                    both_dont_matter_if_unequal = False

            # There are five possibilities of coupled arguments: one
            # of the four combinations differs from the other three,
            # or they are xor'ed

            if ai_doesnt_matter_for_aj_1 and \
               aj_doesnt_matter_for_ai_1 and \
               both_dont_matter_if_unequal:
                # special case is ai=0 aj=0
                args = args[:i] + ((args[i], 'or', args[j]), ) + args[i + 1:]
                lut, args = discard_argument(lut, args, j, False)
                j = i + 1
            elif ai_doesnt_matter_for_aj_1 and \
                 aj_doesnt_matter_for_ai_0 and \
                 both_dont_matter_if_equal:
                # special case is ai=1 aj=0
                args = args[:i] + ((args[i], 'and', negate_expr(args[j])), ) + \
                       args[i + 1:]
                lut, args = discard_argument(lut, args, j, False)
                j = i + 1
            elif ai_doesnt_matter_for_aj_0 and \
                 aj_doesnt_matter_for_ai_1 and \
                 both_dont_matter_if_equal:
                # special case is ai=0 aj=1
                args = args[:i] + ((args[i], 'or', negate_expr(args[j])), ) + \
                       args[i + 1:]
                lut, args = discard_argument(lut, args, j, True)
                j = i + 1
            elif ai_doesnt_matter_for_aj_0 and \
                 aj_doesnt_matter_for_ai_0 and \
                 both_dont_matter_if_unequal:
                # special case is ai=1 aj=1
                args = args[:i] + ((args[i], 'and', args[j]), ) + args[i + 1:]
                lut, args = discard_argument(lut, args, j, True)
                j = i + 1

            elif both_dont_matter_if_equal and \
                 both_dont_matter_if_unequal:
                args = args[:i] + ((args[i], 'xor', args[j]), ) + args[i + 1:]
                lut, args = discard_argument(lut, args, j, False)
                j = i + 1
            else:
                j += 1
        i += 1

    # collect the result

    if not args:
        # constant expression
        assert len(lut) == 1
        return lut

    negate_result = lut.count('1') > lut.count('0')
    if negate_result:
        lut = ''.join('1' if bit == '0' else '0' for bit in lut)

    result = None
    for i, bit in enumerate(lut):
        if bit == '0':
            continue
        expr = None
        for j, arg in enumerate(args):
            if i & (1 << j) == 0:
                arg = negate_expr(arg)
            if expr is None:
                expr = arg
            else:
                expr = (expr, 'and', arg)
        if result is None:
            result = expr
        else:
            result = (result, 'or', expr)

    if negate_result:
        result = negate_expr(result)

    for toplevel_arg in reversed(toplevel_args):
        if len(toplevel_arg) != 4:
            result = tuple(reversed(toplevel_arg)) + (result, )
        elif toplevel_arg[2] == ':':
            result = toplevel_arg[0:2] + (result, ) + toplevel_arg[2:4]
        else:
            assert toplevel_arg[3] == ':'
            result = toplevel_arg + (result, )

    return stringify(result, False)


class Fabric:
    def __init__(self, ic):
        self.ic = ic
        self.tiles = {}
        #self.colbuf = set()

        io_blocks = {}
        ieren_blocks = {}

        for x0, y0, b0, x1, y1, b1 in self.ic.ieren_db():
            i = IOBlock()
            assert (x0, y0, b0) not in io_blocks
            io_blocks[x0, y0, b0] = i
            assert (x1, y1, b1) not in ieren_blocks
            ieren_blocks[x1, y1, b1] = i

        for xy in ic.io_tiles:
            assert xy not in self.tiles
            self.tiles[xy] = IOTile(self, xy,
                                    (io_blocks.pop((xy[0], xy[1], 0), None),
                                     io_blocks.pop((xy[0], xy[1], 1), None)),
                                    (ieren_blocks.pop((xy[0], xy[1], 0), None),
                                     ieren_blocks.pop((xy[0], xy[1], 1), None)))
        assert not io_blocks
        assert not ieren_blocks

        for xy in ic.logic_tiles:
            assert xy not in self.tiles
            self.tiles[xy] = LogicTile(self, xy)

        for xy in ic.ramb_tiles:
            assert xy not in self.tiles
            self.tiles[xy] = RAMBTile(self, xy)

        for xy in ic.ramt_tiles:
            assert xy not in self.tiles
            self.tiles[xy] = RAMTTile(self, xy)

        for x, y in self.tiles:
            assert x >= 0 and x <= self.ic.max_x
            assert y >= 0 and y <= self.ic.max_y
        for x in range(self.ic.max_x + 1):
            for y in range(self.ic.max_y + 1):
                should_exist = (x > 0 and x < self.ic.max_x) or \
                               (y > 0 and y < self.ic.max_y)
                assert ((x, y) in self.tiles) == should_exist

        for xy in ic.ram_data:
            assert type(self.tiles.get(xy, None)) == RAMBTile

        #colbuf_db = ic.colbuf_db()
        #for x, y, i in self.colbuf:
        #    exists = False
        #    for src_x, src_y, dst_x, dst_y in colbuf_db:
        #        if src_x != x or src_y != y:
        #            continue
        #        assert (dst_x, dst_y) in self.tiles
        #        assert not self.tiles[dst_x, dst_y].colbuf[i]
        #        self.tiles[dst_x, dst_y].colbuf[i] = True
        #        exists = True
        #    assert exists
        #
        #for xy in self.tiles:
        #    for br in self.tiles[xy].buffer_and_routing:
        #        if br[0].startswith('glb_netwk_'):
        #            assert self.tiles[xy].colbuf[int(br[0][10:])]

        for bit in self.ic.extra_bits:
            directive, arg = self.ic.lookup_extra_bit(bit)
            assert directive == 'padin_glb_netwk'
            x, y, n = GLB_NETWK_EXTERNAL_BLOCKS[int(arg)]
            assert type(self.tiles.get((x, y), None)) == IOTile
            block = self.tiles[x, y].io_blocks[n]
            assert block is not None
            block.padin_glb_netwk = True

    def printout(self, options):
        print('device "%s" %d %d' % (self.ic.device, self.ic.max_x - 1,
                                                     self.ic.max_y - 1))

        print('')
        # internal_configuration_oscillator_frequency = low | medium | high
        #print('coldboot = off')
        print('warmboot = on')  # IceStorm assumes this to be always on

        for xy in sorted(self.tiles.keys(), key = lambda xy: (xy[1], xy[0])):
            self.tiles[xy].printout(options)

class Tile:
    def __init__(self, fabric, xy, data, is_logic_block):
        self.fabric = fabric
        self.ic = fabric.ic
        self.xy = xy
        self.data = data

        self.buffer_and_routing = set()
        self.used_buffer_and_routing = set()
        self.text = set()
        self.bitinfo = list()
        self.unknown_bits = False

        x, y = xy
        db = self.ic.tile_db(x, y)
        mapped_bits = set()

        # 'data' is a list of strings containing a series of zeroes and
        # ones.  'bits' is a set of strings containing an entry
        # "B<row>[<col>]" or "!B<row>[<col>]" for each bit.

        bits = set()
        for k, line in enumerate(data):
            for i in range(len(line)):
                if line[i] == '1':
                    bits.add('B%d[%d]' % (k, i))
                else:
                    bits.add('!B%d[%d]' % (k, i))

        for entry in db:
            # LC bits don't have a useful entry in the database; skip them
            # for now
            if re.match(r'LC_', entry[1]):
                continue

            # some nets have different names depending on the tile; filter
            # out non-applicable net names
            if entry[1] in ('routing', 'buffer') and (
                    not self.ic.tile_has_net(x, y, entry[2]) or
                    not self.ic.tile_has_net(x, y, entry[3])):
                continue

            # are all required bits set/unset?
            match = True
            for bit in entry[0]:
                if not bit in bits:
                    match = False
            if match:
                for bit in entry[0]:
                    mapped_bits.add(bit)

            if entry[1:] == ['IoCtrl', 'IE_0']:
                if match != (self.ic.device == '1k'):
                    self.ieren_blocks[0].enable_input = True
                continue
            if entry[1:] == ['IoCtrl', 'REN_0']:
                if match:
                    self.ieren_blocks[0].disable_pull_up = True
                continue
            if entry[1:] == ['IoCtrl', 'IE_1']:
                if match != (self.ic.device == '1k'):
                    self.ieren_blocks[1].enable_input = True
                continue
            if entry[1:] == ['IoCtrl', 'REN_1']:
                if match:
                    self.ieren_blocks[1].disable_pull_up = True
                continue

            if entry[1].startswith('IOB_') and entry[2].startswith('PINTYPE_'):
                if match:
                    self.io_blocks[int(entry[1][4:])].pintype \
                        |= 1 << int(entry[2][8:])
                continue

            if entry[1:] == ['RamConfig', 'PowerUp']:
                if match != (self.ic.device == '1k'):
                    self.text.add('power_up')
                continue

            if entry[1] == 'routing':
                if match:
                    src = translate_netname(self.xy[0], self.xy[1],
                                            self.ic.max_x - 1,
                                            self.ic.max_y - 1, entry[2])
                    dst = translate_netname(self.xy[0], self.xy[1],
                                            self.ic.max_x - 1,
                                            self.ic.max_y - 1, entry[3])
                    if dst == 'fabout':
                        dst = lookup_fabout(*self.xy)
                    self.buffer_and_routing.add((src, '~>', dst))
                continue
            if entry[1] == 'buffer':
                if match:
                    src = translate_netname(self.xy[0], self.xy[1],
                                            self.ic.max_x - 1,
                                            self.ic.max_y - 1, entry[2])
                    dst = translate_netname(self.xy[0], self.xy[1],
                                            self.ic.max_x - 1,
                                            self.ic.max_y - 1, entry[3])
                    if dst == 'fabout':
                        dst = lookup_fabout(*self.xy)
                    self.buffer_and_routing.add((src, '->', dst))
                continue

            if entry[1] == 'ColBufCtrl':
                assert entry[2].startswith('glb_netwk_')
                #if match:
                #    fabric.colbuf.add(self.xy + (int(entry[2][10:]), ))
                continue

            if match:
                self.text.add(' '.join(entry[1:]))

        for prefix in ('local_', 'glb2local_'):
            for fst in [fst for fst in self.buffer_and_routing
                        if fst[-1].startswith(prefix)]:
                used = False
                for snd in [snd for snd in self.buffer_and_routing
                            if snd[0] == fst[-1]]:
                    self.buffer_and_routing.remove(snd)
                    self.buffer_and_routing.add(fst[:-1] + snd)
                    used = True
                if used:
                    self.buffer_and_routing.remove(fst)

        for k, line in enumerate(data):
            self.bitinfo.append('')
            extra_text = ''
            for i in range(len(line)):
                if 36 <= i <= 45 and is_logic_block:
                    self.bitinfo[-1] += '*' if line[i] == '1' else '-'
                elif line[i] == '1' and 'B%d[%d]' % (k, i) not in mapped_bits:
                    self.unknown_bits = True
                    extra_text += ' B%d[%d]' % (k, i)
                    self.bitinfo[-1] += '?'
                else:
                    self.bitinfo[-1] += '+' if line[i] == '1' else '-'
            self.bitinfo[-1] += extra_text

    def get_hlc(self):
        return sorted(set.union(self.text,
                                set(' '.join(t)
                                    for t in set.difference(
                                            self.buffer_and_routing,
                                            self.used_buffer_and_routing))))

    def printout(self, stmt, options):
        text = self.get_hlc()
        if text or self.unknown_bits or options.print_all:
            if self.unknown_bits or options.print_map:
                print()
                if self.unknown_bits:
                    print("; Warning: No DB entries for some bits:")
                for k, line in enumerate(self.bitinfo):
                    print("; %4s %s" % ('B%d' % k, line))
            print()
            print("%s %d %d {" % (stmt, self.xy[0], self.xy[1]))
            for line in text:
                print("    " + line)
            print("}")

class LogicCell:
    def __init__(self, tile, lcidx):
        self.lut = ''.join(icebox.get_lutff_lut_bits(tile.data, lcidx))
        self.expr = lut_to_logic_expression(
            self.lut, ('in_0', 'in_1', 'in_2', 'in_3'))

        self.options = []
        lutff_option_bits = ''.join(icebox.get_lutff_seq_bits(tile.data, lcidx))
        if lutff_option_bits[0] == '1': self.options.append('enable_carry')
        if lutff_option_bits[1] == '1': self.options.append('enable_dff')
        if lutff_option_bits[2] == '1': self.options.append('set_noreset')
        if lutff_option_bits[3] == '1': self.options.append('async_setreset')

        self.buffer_and_routing0 = set()
        self.buffer_and_routing1 = set()
        for br in tuple(tile.buffer_and_routing):
            if br[0] == 'lutff_%d/out' % lcidx:
                self.buffer_and_routing1.add((br[0][8:], ) + br[1:])
                tile.used_buffer_and_routing.add(br)
            elif br[-1].startswith('lutff_%d/' % lcidx):
                self.buffer_and_routing0.add(br[:-1] + (br[-1][8:], ))
                tile.used_buffer_and_routing.add(br)

    def get_hlc(self):
        if self.lut == '0000000000000000' and not self.options:
            t = []
        elif len(self.expr) > 64:
            t = ['lut ' + self.lut]
        else:
            t = ['out = ' + self.expr]
        return [' '.join(t) for t in sorted(self.buffer_and_routing0,
                                            key = lambda x: x[-1])] + \
               t + self.options + \
               [' '.join(t) for t in sorted(self.buffer_and_routing1,
                                            key = lambda x: x[-1])]

class LogicTile(Tile):
    def __init__(self, fabric, xy):
        super().__init__(fabric, xy, fabric.ic.logic_tiles[xy], True)
        self.cells = tuple(LogicCell(self, lcidx) for lcidx in range(8))

    def get_hlc(self):
        text = super().get_hlc()

        for i, cell in reversed(tuple(enumerate(self.cells))):
            t = cell.get_hlc()
            if t:
                text = ['lutff_%d {' % i] + \
                       ['    %s' % s for s in t] + \
                       ['}'] + \
                       text

        return text

    def printout(self, options):
        super().printout('logic_tile', options)

class IOBlock:
    def __init__(self):
        # stored in the I/O tile where this block is located
        self.pintype = 0

        # stored in the I/O tile where this is an IE/REN block
        self.enable_input = False
        self.disable_pull_up = False

        # stored as an extra bit
        self.padin_glb_netwk = False

class IOTile(Tile):
    def __init__(self, fabric, xy, io_blocks, ieren_blocks):
        self.io_blocks = io_blocks
        self.ieren_blocks = ieren_blocks
        super().__init__(fabric, xy, fabric.ic.io_tiles[xy], False)
        #self.cells = tuple(IOCell() for i in range(2))

        for i, block in enumerate(io_blocks):
            if block is None:
                continue
            block.buffer_and_routing0 = set()
            block.buffer_and_routing1 = set()
            for br in tuple(self.buffer_and_routing):
                if br[0].startswith('io_%d/D_IN_' % i):
                    block.buffer_and_routing1.add((br[0][5:], ) + br[1:])
                    self.used_buffer_and_routing.add(br)
                elif br[-1].startswith('io_%d/' % i):
                    block.buffer_and_routing0.add(br[:-1] + (br[-1][5:], ))
                    self.used_buffer_and_routing.add(br)

    def get_hlc(self):
        # if io_blocks[N] is None, this means there's no I/O pin there

        text = super().get_hlc()
        for n in (1, 0):
            block = self.io_blocks[n]
            if block is None:
                continue

            t = []
            input_pt = block.pintype & 3
            output_pt = block.pintype >> 2 & 15
            unknown_pt = block.pintype >> 6
            if input_pt != 0:
                t.append('input_pin_type = %s' % (
                    'registered_pin',
                    'simple_input_pin',
                    'latched_registered_pin',
                    'latched_pin')[input_pt])
            if output_pt != 0:
                t.append('output_pin_type = %s' % (
                    'no_output',
                    '1',
                    '2',
                    '3',
                    'DDR',
                    'REGISTERED',
                    'simple_output_pin',
                    'REGISTERED_INVERTED',
                    'DDR_ENABLE',
                    'REGISTERED_ENABLE',
                    'OUTPUT_TRISTATE',
                    'REGISTERED_ENABLE_INVERTED',
                    'DDR_ENABLE_REGISTERED',
                    'REGISTERED_ENABLE_REGISTERED',
                    'ENABLE_REGISTERED',
                    'REGISTERED_ENABLE_REGISTERED_INVERTED')[output_pt])
            if unknown_pt != 0:
                t.append('unknown_pin_type = %d' % unknown_pt)
            if block.enable_input:
                t.append('enable_input')
            if block.disable_pull_up:
                t.append('disable_pull_up')

            t += [' '.join(t) for t in sorted(block.buffer_and_routing0,
                                              key = lambda x: x[-1])]
            t += [' '.join(t) for t in sorted(block.buffer_and_routing1,
                                              key = lambda x: x[0])]
            if block.padin_glb_netwk:
                t += ['GLOBAL_BUFFER_OUTPUT -> glb_netwk_%d'
                        % GLB_NETWK_EXTERNAL_BLOCKS.index(self.xy + (n, ))]

            if t:
                text = ['io_%d {' % n] + \
                       ['    %s' % s for s in t] + \
                       ['}'] + \
                       text

        return text

    def printout(self, options):
        super().printout('io_tile', options)

class IOCell:
    pass

class RAMBTile(Tile):
    def __init__(self, fabric, xy):
        super().__init__(fabric, xy, fabric.ic.ramb_tiles[xy], False)
        if xy in fabric.ic.ram_data:
            self.data = fabric.ic.ram_data[xy]
        else:
            self.data = None

    def get_hlc(self):
        text = super().get_hlc()
        if self.data is not None:
            text.append('')
            text.append('data {')
            for line in self.data:
                text.append('    ' + line)
            text.append('}')
        return text

    def printout(self, options):
        super().printout('ramb_tile', options)

class RAMTTile(Tile):
    def __init__(self, fabric, xy):
        super().__init__(fabric, xy, fabric.ic.ramt_tiles[xy], False)

    def printout(self, options):
        super().printout('ramt_tile', options)


class Options:
    def __init__(self):
        self.print_map = False
        self.print_all = False

def main():
    program_short_name = os.path.basename(sys.argv[0])
    options = Options()

    try:
        opts, args = getopt.getopt(sys.argv[1:], 'mA', ['help', 'version'])
    except getopt.GetoptError as e:
        sys.stderr.write("%s: %s\n" % (program_short_name, e.msg))
        sys.stderr.write("Try `%s --help' for more information.\n"
                         % sys.argv[0])
        sys.exit(1)

    for opt, arg in opts:
        if opt == '--help':
            sys.stderr.write("""\
Create a high-level representation from an ASCII bitstream.
Usage: %s [OPTION]... FILE

  -m                    print tile config bitmaps
  -A                    don't skip uninteresting tiles

      --help            display this help and exit
      --version         output version information and exit

If you have a bug report, please file an issue on github:
  https://github.com/rlutz/icestorm/issues
""" % sys.argv[0])
            sys.exit(0)

        if opt == '--version':
            sys.stderr.write("""\
icebox_asc2hlc - create a high-level representation from an ASCII bitstream
Copyright (C) 2017 Roland Lutz

This program is free software: you can redistribute it and/or
modify it under the terms of the GNU General Public License as
published by the Free Software Foundation, either version 3 of
the License, or (at your option) any later version.

This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
GNU General Public License for more details.
""")
            sys.exit(0)

        if opt == '-m':
            options.print_map = True
        elif opt == '-A':
            options.print_all = True

    if not args:
        sys.stderr.write("%s: missing argument\n" % (program_short_name))
        sys.stderr.write("Try `%s --help' for more information.\n"
                         % sys.argv[0])
        sys.exit(1)

    if len(args) != 1:
        sys.stderr.write("%s: too many arguments\n" % (program_short_name))
        sys.stderr.write("Try `%s --help' for more information.\n"
                         % sys.argv[0])
        sys.exit(1)

    ic = icebox.iceconfig()
    if args[0] == '-':
        ic.read_file('/dev/stdin')
    else:
        ic.read_file(args[0])

    fabric = Fabric(ic)
    fabric.printout(options)

if __name__ == '__main__':
    main()
