Buggy python submission (verdict: Time Limit Exceeded):
import sys
read = sys.stdin.buffer.read
readline = sys.stdin.buffer.readline
readlines = sys.stdin.buffer.readlines

import itertools
import numpy as np

A,B,C = read().decode().split()

A = np.array(list(A))
B = np.array(list(B))
C = np.array(list(C))

M = 2020

def can_match(x,y):
    L = min(len(x), len(y))
    x = x[:L]
    y = y[:L]
    return np.all((x == '?') | (y == '?') | (x == y))

def solve(A,B,C,LA,LB,LC):
    BA = [True] * (M)
    for i in range(M):
        BA[i] = can_match(A[i:], B)
    CA = [True] * (M+M)
    for i in range(M+M):
        CA[i] = can_match(A[i:], C)
    CB = [True] * (M)
    for i in range(M):
        CB[i] = can_match(B[i:], C)
    BA = np.array(BA)
    CA = np.array(CA)
    CB = np.array(CB)
    k = np.arange(M)[:,None] + np.arange(M)[None,:]
    cond = BA[:,None] & CB[None,:] & CA[k]
    length = np.maximum(LA, np.maximum((LB + np.arange(M))[:,None], (LC + k)))
    return length[cond].min()

answer = 10 ** 9
for A,B,C in itertools.permutations([A,B,C]):
    LA = len(A)
    LB = len(B)
    LC = len(C)
    x = solve(A,B,C,LA,LB,LC)
    if answer > x:
        answer = x
print(answer)

Fixed submission:
import sys
read = sys.stdin.buffer.read
readline = sys.stdin.buffer.readline
readlines = sys.stdin.buffer.readlines

import itertools

A,B,C = read().decode().split()

A = list(A)
B = list(B)
C = list(C)

def can_match(x,y):
    return x == '?' or y == '?' or x == y

M = 2020

def solve(A,B,C,LA,LB,LC):
    B_from_A = [True] * (M+1)
    for i in range(M+1):
        B_from_A[i] = all(can_match(x,y) for x,y in zip(A[i:],B))
    C_from_A = [True] * (M+M+1)
    for i in range(M+M+1):
        C_from_A[i] = all(can_match(x,y) for x,y in zip(A[i:],C))
    C_from_B = [True] * (M+1)
    for i in range(M+1):
        C_from_B[i] = all(can_match(x,y) for x,y in zip(B[i:],C))
    for i in range(M):
        if not B_from_A[i]:
            continue
        for j in range(M):
            if not C_from_B[j]:
                continue
            if not C_from_A[i+j]:
                continue
            yield max(LA, LB+i, LC+i+j)
            break

answer = 10 ** 9
for A,B,C in itertools.permutations([A,B,C]):
    LA = len(A)
    LB = len(B)
    LC = len(C)
    x = min(solve(A,B,C,LA,LB,LC))
    if answer > x:
        answer = x
print(answer)

Buggy python submission (verdict: Time Limit Exceeded):
import sys
read = sys.stdin.buffer.read
readline = sys.stdin.buffer.readline
readlines = sys.stdin.buffer.readlines

import itertools

A,B,C = read().decode().split()

A = list(A)
B = list(B)
C = list(C)

def can_match(x,y):
    return x == '?' or y == '?' or x == y

M = 2020

def solve(A,B,C,LA,LB,LC):
    B_from_A = [False] * (M+M+1)
    for i in range(M+M+1):
        B_from_A[i] = all(can_match(x,y) for x,y in zip(A[i:],B))
    C_from_A = [False] * (M+M+1)
    for i in range(M+M+1):
        C_from_A[i] = all(can_match(x,y) for x,y in zip(A[i:],C))
    C_from_B = [False] * (M+M+1)
    for i in range(M+M+1):
        C_from_B[i] = all(can_match(x,y) for x,y in zip(B[i:],C))
    for i in range(M):
        if not B_from_A[i]:
            continue
        for j in range(i,i+M):
            if not C_from_A[j]:
                continue
            if not C_from_B[j-i]:
                continue
            yield max(LA, LB+i, LC+j)

answer = 10 ** 9
for A,B,C in itertools.permutations([A,B,C]):
    LA = len(A)
    LB = len(B)
    LC = len(C)
    x = min(solve(A,B,C,LA,LB,LC))
    if answer > x:
        answer = x
print(answer)



Fixed submission:
import sys
read = sys.stdin.buffer.read
readline = sys.stdin.buffer.readline
readlines = sys.stdin.buffer.readlines

import itertools

A,B,C = read().decode().split()

A = list(A)
B = list(B)
C = list(C)

def can_match(x,y):
    return x == '?' or y == '?' or x == y

M = 2020

def solve(A,B,C,LA,LB,LC):
    B_from_A = [True] * (M+1)
    for i in range(M+1):
        B_from_A[i] = all(can_match(x,y) for x,y in zip(A[i:],B))
    C_from_A = [True] * (M+M+1)
    for i in range(M+M+1):
        C_from_A[i] = all(can_match(x,y) for x,y in zip(A[i:],C))
    C_from_B = [True] * (M+1)
    for i in range(M+1):
        C_from_B[i] = all(can_match(x,y) for x,y in zip(B[i:],C))
    for i in range(M):
        if not B_from_A[i]:
            continue
        for j in range(M):
            if not C_from_B[j]:
                continue
            if not C_from_A[i+j]:
                continue
            yield max(LA, LB+i, LC+i+j)
            break

answer = 10 ** 9
for A,B,C in itertools.permutations([A,B,C]):
    LA = len(A)
    LB = len(B)
    LC = len(C)
    x = min(solve(A,B,C,LA,LB,LC))
    if answer > x:
        answer = x
print(answer)