We are currently working on new rules for what content should and shouldn't be allowed on this website, and are looking for feedback! See Esolang:2026 topicality proposal to view and give feedback on the current draft.

Typeid

From Esolang
Jump to navigation Jump to search

Typeid is an esolang invented by User:None1, inspired by Brain-Flak and brainf*ck (not brainfuck). It uses Itanium ABI mangled types as programs. It's pronounced /ˈtaɪpeɪd/.

Typeid
Paradigm(s) procedural, imperative
Designed by User:None1
Appeared in 2026
Type system untyped
Memory system stack-based
Dimensions one-dimensional
Computational class Turing-complete
Major implementations Python
Influenced by Itanium ABI, Brain-Flak and brainf*ck
File extension(s) .ty

Memory

It has a stack with unbounded integers. Popping from an empty stack results in 0.

Commands

Built-in Types

Types that aren't mentioned here but valid in Itanium ABI are NOPs which return 0, and so are names in the std namespace (even if they're made up, like std::fuck) that aren't listed in the table.

Command Meaning in Typeid Meaning in Itanium ABI
a Input a character and return it signed char
b Input an integer and return it bool
c Pop stack and print as ASCII, returns 0 char
d Pop stack and print as integer, returns 0 double
e The same as c, but returns the value popped long double
f The same as d, but returns the value popped float
g Returns 0 __float128
h Returns 1 unsigned char
i Pop a and b, return b+a int
j Pop a and b, return b-a unsigned int
l Pop a and b, return b*a long
m Pop a and b, return floor(b/a) unsigned long
n Pop a and b, return b%a __int128
o Pop a and b, return ba unsigned __int128
s Swap top stack values, return 0 short
t Perform a left circular shift on the three top stack values (a b c)->(b c a) unsigned short
v Pop a and b, return a bitwise AND b void
w Pop a and b, return a bitwise OR b wchar_t
x Pop a and b, return a XOR b long long
y Pop a, return ~a unsigned long long
z Pop a, return -a ...
Sa Return a random integer within [0,1] std::allocator
Sb Pop x, Return a random integer within [1,x] std::basic_string
Sd Return the current UNIX timestamp as an integer std::iostream
Si Return the length of the stack std::istream
So Pop x, return sign(x) std::ostream
Ss Pop a C-style string (Pop all the numbers until top is zero) from the stack and print it, returns 0 std::string

Input commands all return 0 when they encounter EOF or invalid input.

A pointer type (Ptype) to a type pushes the return value of that type onto the stack and returns it.

A const type (Ktype) to a type prints the return value of it as an ASCII character and returns it.

A reference type (Rtype) to a type prints the return value of it as an integer and returns it.

Custom types

Namespace names/Types without template arguments

Their names are simply printed when they're executed. 0 is returned.

Types with template arguments

Their exact names don't matter. Instead, the lengths of them do.

The syntax is like this (spaces are just for clarity):

length name I arguments E
Length Meaning
1 Return the sum of all arguments
2 Return the product of all argments
3 While top of stack is nonzero, execute the arguments as code. Return the sum of all runs
4 While top of stack is zero, execute the arguments as code. Return the sum of all runs
5 While stack is nonempty, execute the arguments as code. Return the sum of all runs
6 While stack is empty, execute the arguments as code. Return the sum of all runs
7 If top of stack is nonzero, execute the arguments as code. Return the sum of all arguments
8 If top of stack is zero, execute the arguments as code. Return the sum of all arguments
9 If stack is nonempty, execute the arguments as code. Return the sum of all arguments
10 If stack is empty, execute the arguments as code. Return the sum of all arguments
11 Execute the arguments as code forever
12 and above Execute the arguments as code. Return length-12 (regardless of its arguments' results)

Examples

Cat

4fourIKaE

Demangled:

four<signed char const>

Hello, world!

N5Hello1_IK2aaI1aIhhhhE1bIhhhhhhhhhhhEEK2bbI1cIhhhhE1dIhhhhhhhhEE5worldK2ccI1eIhhhE1fIhhhhhhhhhhhEEEE

Demangled:

Hello::_<aa<a<unsigned char, unsigned char, unsigned char, unsigned char>, b<unsigned char, unsigned char, unsigned char, unsigned char, unsigned char, unsigned char, unsigned char, unsigned char, unsigned char, unsigned char, unsigned char>> const, bb<c<unsigned char, unsigned char, unsigned char, unsigned char>, d<unsigned char, unsigned char, unsigned char, unsigned char, unsigned char, unsigned char, unsigned char, unsigned char>> const, world, cc<e<unsigned char, unsigned char, unsigned char>, f<unsigned char, unsigned char, unsigned char, unsigned char, unsigned char, unsigned char, unsigned char, unsigned char, unsigned char, unsigned char, unsigned char>> const>

A+B

R1_IbbE

Demangled:

_<bool, bool>&

Truth Machine

1_IRPb3aaaIPfEE

Demangled:

_<bool*&, aaa<float*> >

XKCD Random Number

49choosen_by_fair_dice_roll_guaranteed_to_be_randomIR1aIhhhhEE

Demangled:

choosen_by_fair_dice_roll_guaranteed_to_be_random<a<unsigned char, unsigned char, unsigned char, unsigned char>&>

Computational class

Turing complete, because it can be translated from 3-cell brainfuck:

3-cell brainfuck to Typeid translation
3-cell brainfuck Typeid
begin
1aIPgPgPg
>
tt
<
t
+
PhPi
-
PhPj
[
3aaaI
]
E
end
E

Implementations

In Python. Uses the itanium_demangler package:

from itanium_demangler import *
import sys
from random import *
from time import *
from math import prod

sys.setrecursionlimit(2147483647)
code = parse("_Z1_" + input())
if not code:
    raise SyntaxError("Invalid code")
code = code.arg_tys[0]
stack = []
pop = lambda: stack.pop() if stack else 0
get = lambda: stack[-1] if stack else 0


def interpret(code):
    if code.kind == "builtin":  # built-in types, Sx types are in 'qualname'
        match code.value:
            case "signed char":  # a
                c = sys.stdin.read(1)
                return ord(c) if c else 0
            case "bool":  # b
                try:
                    z = int(input())
                except:
                    z = 0
                return z
            case "char":  # c
                print(chr(pop()), end="", flush=True)
                return 0
            case "double":  # d
                print(pop())
                return 0
            case "__float80":  # e
                _ = pop()
                print(chr(_), end="", flush=True)
                return _
            case "float":  # f
                _ = pop()
                print(_)
                return _
            case "__float128":
                return 0
            case "unsigned char":
                return 1
            case "int":
                a, b = pop(), pop()
                return b + a
            case "unsigned int":
                a, b = pop(), pop()
                return b - a
            case "long":
                a, b = pop(), pop()
                return b * a
            case "unsigned long":
                a, b = pop(), pop()
                return b // a
            case "__int128":
                a, b = pop(), pop()
                return b % a
            case "unsigned __int128":
                a, b = pop(), pop()
                return b**a
            case "short":
                a, b = pop(), pop()
                stack.append(a)
                stack.append(b)
                return 0
            case "unsigned short":
                c, b, a = pop(), pop(), pop()
                stack.append(b)
                stack.append(c)
                stack.append(a)
                return 0
            case "void":
                a, b = pop(), pop()
                return b & a
            case "wchar_t":
                a, b = pop(), pop()
                return b | a
            case "long long":
                a, b = pop(), pop()
                return b ^ a
            case "unsigned long long":
                a = pop()
                return ~a
            case "...":
                a = pop()
                return -a
            case _:
                return 0
    elif code.kind == "pointer":
        _ = interpret(code.value)
        stack.append(_)
        return _
    elif code.kind == "lvalue":
        _ = interpret(code.value)
        print(_)
        return _
    elif code.kind == "cv_qual" and "const" in code.qual:
        _ = interpret(code.value)
        print(chr(_), end="", flush=True)
        return _
    elif code.kind == "name":
        print(code.value, end="", flush=True)
        return 0
    elif code.kind == "qual_name":
        if code.value[0] == "std":
            if len(code) == 2 or len(code) == 3 and code[2].kind == "tpl_args":
                match code.value[1]:
                    case "allocator":
                        return randint(0, 1)
                    case "basic_string":
                        return randint(1, pop())
                    case "iostream":
                        return int(time())
                    case "istream":
                        return len(stack)
                    case "ostream":
                        x = pop()
                        if x < 0:
                            return -1
                        elif x > 0:
                            return 1
                        return 0
                    case "string":
                        while get():
                            z = pop()
                            if not z:
                                break
                            print(chr(z), end="", flush=True)
                    case _:
                        return 0
            else:
                return 0
        else:
            has_tpl = False
            for i in code.value:
                if i.kind == "tpl_args":
                    has_tpl = True
                    break
            if not has_tpl:
                for i in code.value:
                    print(i.value, end="", flush=True)
            else:
                for i in range(len(code.value) - 2):
                    print(code.value[i].value,end='', flush=True)
                args = code.value[-1].value
                match len(code.value[-2].value):
                    case 1:
                        return sum(interpret(i) for i in args)
                    case 2:
                        return prod(interpret(i) for i in args)
                    case 3:
                        result = 0
                        while get():
                            result += sum(interpret(i) for i in args)
                        return result
                    case 4:
                        result = 0
                        while not get():
                            result += sum(interpret(i) for i in args)
                        return result
                    case 5:
                        result = 0
                        while len(stack):
                            result += sum(interpret(i) for i in args)
                        return result
                    case 6:
                        result = 0
                        while not len(stack):
                            result += sum(interpret(i) for i in args)
                        return result
                    case 7:
                        result = 0
                        if get():
                            result += sum(interpret(i) for i in args)
                        return result
                    case 8:
                        result = 0
                        if not get():
                            result += sum(interpret(i) for i in args)
                        return result
                    case 9:
                        result = 0
                        if len(stack):
                            result += sum(interpret(i) for i in args)
                        return result
                    case 10:
                        result = 0
                        if not len(stack):
                            result += sum(interpret(i) for i in args)
                        return result
                    case 11:
                        while 1:
                            for i in args:
                                interpret(i)
                    case _:
                        for i in args:
                            interpret(i)
                        return len(code.value[-2]) - 12
    else:
        return 0


interpret(code)