def cast(obj):
        """Converts ``obj`` to an Amaranth constant.

        First, ``obj`` is converted to a value using :meth:`Value.cast`. If it is a constant, it
        is returned. If it is a constant-castable expression, it is evaluated and returned.
        Otherwise, :exn:`TypeError` is raised.
        """
        obj = Value.cast(obj)
        if type(obj) is Const:
            return obj
        elif type(obj) is Concat:
            value = 0
            width = 0
            for part in obj.parts:
                const  = Const.cast(part)
                part_value = Const(const.value, unsigned(len(const))).value
                value |= part_value << width
                width += len(const)
            return Const(value, width)
        elif type(obj) is Slice:
            value = Const.cast(obj.value)
            return Const(value.value >> obj.start, unsigned(obj.stop - obj.start))
        else:
            raise TypeError(f"Value {obj!r} cannot be converted to an Amaranth constant")
Converts ``obj`` to an Amaranth constant.

        First, ``obj`` is converted to a value using :meth:`Value.cast`. If it is a constant, it
        is returned. If it is a constant-castable expression, it is evaluated and returned.
        Otherwise, :exn:`TypeError` is raised.
        
amaranth/hdl/_ast.py